###### tags: `會議紀錄`
###### Thunder: `權限設定`
###### CodeReview: `OneSignal(訊息推播)` `GoogleMap(地圖)` `this.injector.get()`
###### Announcement: `SD需求 #GA碼` `SD需求 #權限需求`
###### Attendee: 政儀、永佳、偉恩、弘翊、政儒
# 📌[R]2020/02/11前端會議
## 踩雷事件
### ⚡權限設定
:::info
說明:
* 新增CRM模組,權限判斷需要大改。
* 舊的AuthGuard(auth-guard.service.ts)決定不維護。
=>已經修改太多次裡面東西太多了
* 新增一支新的CrmGaurd(crm-auth.guard.ts)來做新的權限判斷。
=>舊的還是留著
:::
A1的權限判斷是寫在xxx-routing.module.ts裡面,透過canActicate執行AuthGuard這支程式來判斷權限。例:
```typescript
const routes: Routes = [
{ path: 'auth_pos', component: AuthPosComponent, canActivate: [AuthGuard], data: { jobID: JOBID.GENERAL }}
];
```
新增CRMAuthGuard後,也將他加在canActivate裡,
```typescript
const routes: Routes = [
{ path: 'auth_pos', component: AuthPosComponent, canActivate: [AuthGuard, CRMAuthGuard], data: { jobID: JOBID.GENERAL }},
{ ... canActivate: [AuthGuard, CRMAuthGuard] ...}
];
```
但因為canActivate的陣列,型別要屬於下列三種之一
* Observable<boolean | UrlTree>
* Promise<boolean | UrlTree>
* boolean | UrlTree;
AuthGuard是屬於Promise,CrmGaurd目前可能會回傳Observable/boolean,因此就會有非同步問題。
#### #1 canActivate兩支為非同步
如果兩個同時向後端發出相同請求,後面發出請求的會被取消發生錯誤。
==💡解決方法: 將共同呼叫API寫在一支service內一起管理(有一方先拿到值就將它存進變數裡,後面的就直接拿變數內的值)。==
#### #2 取得不同份service資料(#1延伸問題)
在不同的**.module.ts providers掛上service,導致service實體化兩次(會優先取上一層的service),兩支canActivate內的資料不一致。
==💡解決方法:將共用的service掛在最外層。==
## 寫法交流
### ⛏OneSignal(訊息推播)
[永佳onesignal筆記](https://www.notion.so/onesignal-bff1478608c5461db012a6c45f4d671e)
#### #1 OneSignal設定
可以參考下面兩個網址設定
[OneSignal官網](https://onesignal.com/)
[OneSignal文件](https://documentation.onesignal.com/docs)
程式
```typescript
platform.ready().then(() => {
statusBar.styleDefault();
splashScreen.hide();
const notificationOpenedCallback = function (jsonData) {
console.log('notificationOpenedCallback: ' + JSON.stringify(jsonData));
};
window["plugins"].OneSignal
.startInit("584f8cff-218c-4942-986e-2e6c647faa93", "614728355810")
.handleNotificationOpened(notificationOpenedCallback)
.inFocusDisplaying(window["plugins"].OneSignal.OSInFocusDisplayOption.Notification)
.endInit()
});
```
#### #2 window["plugins"].OneSignal
[1]
```typescript
window["plugins"].OneSignal
.startInit("584f8cff-218c-4942-986e-2e6c647faa93", "614728355810")
.handleNotificationOpened(notificationOpenedCallback)
.inFocusDisplaying(window["plugins"].OneSignal.OSInFocusDisplayOption.Notification)
.endInit()
```
[2]
```typescript
window["plugins"].OneSignal.startInit("584f8cff-218c-4942-986e-2e6c647faa93", "614728355810")
window["plugins"].OneSignal.handleNotificationOpened(notificationOpenedCallback)
window["plugins"].OneSignal.inFocusDisplaying(window["plugins"].OneSignal.OSInFocusDisplayOption.Notification)
window["plugins"].OneSignal.endInit();
```
這兩個寫法是一樣的意思,.startInit/.handleNotificationOpened/.inFocusDisplaying/.endInit都是指向`window["plugins"].OneSignal`。
#### #3 sendTags()特別寫法
但是sendTags()不可以使用(#2)第一種寫法要用第二種寫法,若使用第一種的需要抽開寫。
```typescript
window["plugins"].OneSignal
.startInit("584f8cff-218c-4942-986e-2e6c647faa93", "614728355810")
.handleNotificationOpened(notificationOpenedCallback)
.inFocusDisplaying(window["plugins"].OneSignal.OSInFocusDisplayOption.Notification)
.endInit();
window["plugins"].OneSignal.sendTag("UserID4", "0")
```
#### #4 介面訊息
OneSignal> Audience> AllUsers
可以查看訂閱者的相關訊息(最近使用/第一次使用/用sendTag()傳送的訊息 等... ...)。


### ⛏GoogleMap(地圖)
#### #1 轉址
使用GoogleMap會產生的費用: 經緯轉換地址/地址轉換經緯。
* 行動版: 無任何費用
* 網頁版: 需支付轉址費用(1000次7美金)
行動版使用ionic套件,所以可以免費使用
> 政儀寫在PositionProcessProvider(position-process.ts)裡,可以參考看看。
```typescript
import { NativeGeocoder } from '@ionic-native/native-geocoder';
```
```typescript
/**經緯轉換地址 行動裝置才可正常運做*/
getAddress(position: Position): Observable<string> {
let subscriber: Subscriber<string>;
const observable = new Observable((x: Subscriber<string>) => { subscriber = x; });
console.log('currentLatitude = ', position.lat);
console.log('currentLongitude = ', position.lng);
this.nativeGeocoder.reverseGeocode(position.lat, position.lng)
.then((result: NativeGeocoderReverseResult[]) => {
// console.log('result 2 = ', JSON.stringify(result[0]));
console.log('result = ', result);
// const newResult: NativeGeocoderResultModel = JSON.parse(JSON.stringify(result));
const newResult = result[0];
const address = newResult.postalCode + newResult.administrativeArea + newResult.locality + newResult.subLocality + newResult.thoroughfare + newResult.subThoroughfare;
console.log('address = ', address);
subscriber.next(address);
subscriber.complete();
}, (error) => {
console.log(error);
const x = new CheckError('轉換地址失敗');
subscriber.error(x);
});
return observable;
}
/**地址經緯轉換 行動裝置才可正常運做*/
forwardGeocode(address: string) {
let subscriber: Subscriber<Position>;
const observable = new Observable((x: Subscriber<Position>) => { subscriber = x; });
this.nativeGeocoder.forwardGeocode(address)
.then((result: NativeGeocoderForwardResult[]) => {
console.log('result = ', result);
const newResult = result[0];
subscriber.next({ lat: +newResult.latitude, lng: +newResult.longitude });
subscriber.complete();
}, (error) => {
console.log(error);
const x = new CheckError('轉換地址失敗');
subscriber.error(x);
});
return observable;
}
```
但網頁版是交給後端轉址,但後端沒有套件可以使用,因此會產生費用。
#### #2 Google Cloud Platform
要使用google map的API,需要去Google Cloud Platform設定才可以使用。
#### #3 網址生成圖片
使用別人提供的網址,後面加上參數就可以改變顏色/數字。
> 政儀寫在ClockOnPage(clock-on.ts) getMarkerIcon,可以參考看看。
```typescript
private getMarkerIcon(character: number) {
const colors = ['red', 'black', 'blue', 'green', 'grey', 'orange', 'purple', 'white', 'yellow'];
const colorIndex = Math.floor((Math.random() * colors.length));
const icon = `https://raw.githubusercontent.com/Concept211/Google-Maps-Markers/master/images/marker_${colors[colorIndex]}${character}.png`;
return icon;
}
```
### ⛏this.injector.get()
CommonFn內有些this.injector.get(***)的寫法
```typescript
const userPowerService = this.injector.get(UserPowerService);
```
是為了解決相依迴圈的不好寫法,所以***未來應要避免使用***。
## 事情公告
### 📢SD需求
#### #1 GA碼
埋GA碼的要求:希望可以知道使用者是由哪個入口進入、廣告點擊數=>所以先暫時不管
#### #2 權限需求
目前SD的權限需求太過奇怪,還會重新調整