2020年12月24日 星期四

nginx透過Reserver Proxy到docker grafana設定

grafana預設跑在3000的port上

要讓nginx可以upstream到grafana上

並不能只是在nginx上設定

grafana的init設定檔 也需要對應設定


為了讓我們方便管理

可以透過 ansible 將本機準備好的grafana.ini丟到遠端主機上

再透過docker volumn對應 將這ini檔案 對應到container內設定檔的位置

docker-compose 設定

version: '3.8'
services:
  grafana:
    image: grafana/grafana
    container_name: grafana99
    restart: always
    volumes:
        - grafana_data:/var/lib/grafana
        - /home/ozzy/docker_share/monitor/grafana.ini:/etc/grafana/grafana.ini:ro
    environment:
      - GF_SECURITY_ADMIN_PASSWORD=xxxx
    depends_on:
      - prometheus
    ports:
      - '3000:3000'

grafana.ini設定

instance_name = ozzysun.com
protocol = http
http_port = 3000
domain = ozzysun.com
enforce_domain = true
root_url = http://ozzysun.com/grafana
serve_from_sub_path = true
nginx端設定

location /grafana/ {
    proxy_pass http://192.168.0.99:3000;
    proxy_set_header Host       $http_host;
    proxy_set_header X-Real-IP    $remote_addr;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}

test

2020年12月22日 星期二

docker prometheus 儲存資料設定

當使用docker執行prometheus 有一個問題是

當有更改設定檔或是重新啟動服務

所有的資料就都清空了

要確保資料可以長久保留下來

需要將儲存資料的目錄mount到host上的資料夾


在prometheus內資料是存放在container內的 /prometheeus/data目錄下

通常docker container透過volume 去mount指定目錄就可以

但可能會遇到目錄的權限問題

open data/queries.active: permission denied


必須要將mount的host目錄權限設定與執行promethus的使用者權限才可以

譬如說我在docker compose設定以root來執行promethus

則要mount的目錄的owner 就必須要是root


 docker-compose.yml內容  
 version: '3.8'  
 services:  
  prometheus:  
   image: prom/prometheus:latest  
   user: "0:0"  
   container_name: prometheus99  
   restart: always  
   volumes:  
    - /home/ozzy/docker_share/prometheus/prometheus.yml:/etc/prometheus/prometheus.yml:ro  
    - /home/ozzy/docker_share/prometheus/prometheus_data:/prometheus  
   environment:  
    - GO15VENDOREXPERIMENT=1  
   command:  
    - '--config.file=/etc/prometheus/prometheus.yml'  
   ports:  
    - '9090:9090'  
說明
通常我會使用ansible來管理docker的佈署與更新
先將需要維護的設定檔 透過ansible 由開發本機複製到遠端主機host的指定目錄下
接下來再經由docker container mount volume到這指定的目錄下
來達到docker的資料管理都可以在遠端的host上

個人在這個地方卡了一些時間是因為
使用ansible在遠端主機上建立目錄
是指定了become: true也就是使用root建立
但在docker-compose內我並沒有特別設定執行的user
因次premethus是使用遠端主機登入的使用者ozzy執行
造成了寫紀錄的目錄與執行service是不同使用者而
造成權限問題
docker-compose設定的使用者是以設定UID
如果要查uid 可以使用以下指令
顯示目前使用者uid
echo $UID

顯示所有使用者id

 awk -F: '{printf "%s:%s\n",$1,$3}' /etc/passwd  

如果要進入promethus container內 注意 內部並沒有bash 需要改呼叫sh


docker exec -it grafanaContainer sh

2020年12月10日 星期四

nodejs express 非同步錯誤處理的error傳遞

情境

route main內執行 child()

child為非同步

非同步的child function可以是


1.以async宣告
const asyncFun = async(res) => {
  await sleep(2000)
  const result = JSON.parse(body)
  return result
}
2.以Promise宣告
const promiseFun = (res) => {
  return new Promise((resolve, reject) => {
    try {
      const result = JSON.parse(body)
      resolve(result)
    } catch (e) {
      reject(e)
    }
  })
}

如果child function內沒有使用try catch包裹

發生錯誤就會是往呼叫端(main)的catch丟
如果呼叫端(main)也沒有用try catch或是asyc 的catch攔截
錯誤就會往外 讓express的錯誤處理接收到

有一個特別的例外是當child內有使用setTimeout把執行的工作包裝起來
那麼當發生錯誤時
若在child內寫try catch是可以攔截到 但卻無法把錯誤往呼叫端丟
唯一可行的是child是使用promise寫 就可以在try catch攔截到錯誤
時呼叫reject回傳給呼叫端的catch

儘可能不要在child內直接處理res回應
否則當child發生錯誤 res回應的部份不被執行
可能造成系統掛掉

2020年12月8日 星期二

node express async程式發生錯誤時的幾種狀況

 

當執行的async程式發生錯誤時的幾種狀況

一.以try catch 包覆整個程式

1.try catch 包覆外的程式

  無論有無錯誤發生都會被執行

  常見的Cannot set headers after they are sent to the client錯誤 就是這樣發生

2.在try區塊內發生錯誤

  會直接跳到catch區塊,try內其他往下程式碼不會被執行到

3.只要有catch區塊存在

  系統會認為你有處理 就不會主動把錯誤往外丟

4.catch區塊內 以reject回應

  以reject回應錯誤,會回到呼叫端的catch

  若呼叫端沒有catch 則會在這裡發生錯誤

5.catch區塊內 以next回應

  會跳到整個app 的錯誤處理機制上

  也就是進入使用app.use()的部份處理

  

二. 沒有try catch

1.function內

  會直接發生錯誤

2.route內

  會自動往next丟 給外部的錯誤處理

2020年12月7日 星期一

妹妹補假的禮拜一

原是上班時間的禮拜一

因為學校運動會後的補假

我也請了一天假在家


老媽不在家

起床後 開始忙碌的一個早上

把衣服丟到洗衣機洗

再出門運動 發現貓在車下大便

洗了洗地板

妹妹起床 一起出門吃完早餐

再把車開去洗車廠洗車

回到家 帶妹去剪完頭髮

曬完衣服 再回家把地板用漂白水

把被貓大便過的地板 再清潔一次

煮了水餃午餐吃完

也剛好可以把洗好的車開回來

終於 一個早上把所有的事都做完


休息一下 就繼續下午跟妹要去夢時代

要去夢時代 其實是要去透幣唱歌

非假日 夢時代沒有什麼人

逛起來 很輕鬆

走到了心之和 停下來休息吃個蛋糕

喝個飲料 再上6樓唱歌

一首歌要30 實在有點貴

許多的歌還都點不到

大部份時間妹妹都是自己拿著麥克風

自己唱的很開心


晚上妹還有打鼓的課 我們也不能太晚回家

也還要趕7點倒垃圾


吃了乾麵當晚餐

送妹去上打鼓課

妹妹說 每次都是我跟老師很有話聊

聊樂器 聊音樂 聊耳機 唱盤

有一樣音樂喜好 就是可以聊到忘我






2020年12月6日 星期日

我們的旅行— 舊鐵橋 旗山

騎機車 出遊 是妹妹跟我最喜歡的旅遊方式

在fb上看到高雄市政府宣傳大樹的在地旅遊

想到其實在妹妹剛上小學時

我們也去過一次舊鐵橋

沒事的一天 就再去走走


騎著車 由鳳山往屏東的方向 一直騎

過了大寮 到高屏橋下往大樹方向走 就是了

路上妹妹一樣是一路唱著歌

很快就到了舊鐵橋

我們還找出了六年前拍的照片

當時妹妹才剛上小學一年級

今年已經是將畢業的六年級生了



想到以前88快速道路還沒好

要去家裡的果園會是走高屏大橋

清明要去掃墓 走的就是這條往大樹的方向 去杉林

這條路一直走 就是旗山了


妹妹沒去過旗山 說好了 我們就騎著車繼續前進

一路上 經過了佛光山 再往旗山

路途是遠了許多

妹妹像是不會累 還是一路唱著歌


到了旗山老街 走走拍拍照

才吃了一個臭豆腐 妹妹就想要回家了

這樣的旅行方式

也許可以讓妹妹 記得很久 很久


還沒結束!!

回到家4點多 我已經有點累了 妹還是精神很好

答應帶他去新倔江逛 稍微咪了一下

6點半多 還是出發了

到處逛逛走走

買了件衣服 再去買了些diy的線材

妹妹 也覺得累了






2020年12月5日 星期六

運動會


這禮拜就是妹妹學校的運動會

今年六年級了 也是國小最後一年的運動會

早上送妹妹去學校

先開車載老媽去屏東 再開車回來

回到家 也差不多9點半的時間

剛好可以趕上妹妹的趣味競賽


到學校操場上沒看到妹妹班級 時間還沒到

等到快11點才是高年級的活動


下午的大隊接力 結束 閉幕典禮

結束了今天全部的活動 也是妹妹六年級的運動會


每年 我都會來參加 有拍下了妹妹的照片

看著照片 妹妹 長大了

一年級


二年級

三年級


四年級

5年級

六年級








2020年11月15日 星期日

打工的工廠 - 信泰橡膠工業

 這幾天忽然想起升大三的暑假

打工的那些日子


1991年要升大三的那個暑假

沒有回高雄 留在台北打工

因為 想買了一把新的電吉他

白天在新莊找到了一家橡膠工廠打工

晚上去板橋家教


橡膠工廠在新莊的民安路

已經忘記自己在裡面是做什麼樣的工作

打工 應該就是打雜之類的

只記得裡面兩個主要的師傅

一個壯壯禿頭的中年男子

總是帶著我工作

那是一個機台 放入橡膠原料 然後會擠出

成型的條狀橡膠 經過刀切過後

變成了一個個小白塊 經過加熱

就成了一塊塊的橡皮擦


另一個瘦瘦留著小鬍子的師傅

機器擠出來的是長條狀的橡膠

開始繞著一個大圓盤 一圈又一圈的繞著

等裝滿了 吊拉去加熱烤過

再切成一小塊一小塊的就是鉛筆後面那小小圓圓的橡皮擦


工廠裡充滿著橡膠的味道

中午休息時間

大家拿著便當到事務所

看著天天開心 配飯吃

吃完飯 自己拿了紙板

在工廠裡找個地方鋪著就休息


還記得工廠樓上的會計姊姊

以前也是輔大的學姊


工作時 比較輕鬆包裝東西

跟許多的歐巴桑 坐在工廠內

電台廣播總是放得很大聲


這樣的畫面與氣味 到現在都還記得

記得每個人都是那麼的和善對你

告訴你 如果要打工可以再回來

不過 之後 卻再也沒回去過


前幾天晚上忽然想到

在網路上查了一切 找到了信泰橡膠工廠

已經歇業了

看看地圖上的街景

確實就是 打工的那個地方

不知道 大家是否都還安好 健在

Space Song - Beach House

 


最近一直聽著beach house ,也許是適合這個季節,也許如同歌詞般的讓人掉入某一個時空點內

2020年11月8日 星期日

時間

當覺得時間過得愈來越快

六年時間彷彿只是昨日

多希望時間能停留在過去

至少停留在現在

這樣

父母不會再變老

孩子不會再長大


這樣

永遠 就沒有失去

永遠就是永遠

  

2020年11月5日 星期四

The Trip - Still Corners

時光流逝 是該打包你的行李

開始你的旅程的時候

心 不想就這樣的逝去

旅程 讓我們還有活著的感覺



2020年11月3日 星期二

virtualbox NAT網路使用

紀錄一下在vm上網路設定的相關需求

1.Bridge

通常網路設定為bridge是為了可以讓vm與外部直接互通

互通時以與host使用相同的gateway 取得與host同區段的ip對外

host與vm互相ping都是可以通的

2.NAT

設定為NAT則是讓vm可以上網 但外部無法直接ping到vm

設定NAT預設vm內取得的網段為10.0.x.x

vm 可以ping到host 但host卻無法ping到vm

vm本身自成一個區塊獨立與其他都不能互通

如果要讓vm內的服務可以讓host使用

執需要透過設定port forward轉port使用


3.NAT網路

NAT的特性為vm自成一個網路block

若要讓多個vm可以互相ping到 則可以使用NAT網路


要使用NAT網路需先在virtualbox建立NAT網路

檔案/喜好設定/網路/NAT網路 新增至少一筆的網路設定

然後在vm的設定部份

網路卡選擇使用NAT網路後 可以選擇到virtualbox剛設定的natnetwork

如果要作port forward

NAT是在設定網路卡時設定

但NAT網路則是設定在 virtualbox管理的所有nat網路上


當要讓多個vm互通可以讓每個vm網卡都是使用nat網路

且在設定nat網路時都是選擇同一個NAT network就可以互通了

2020年10月14日 星期三

Error response from daemon: cannot stop container 無法停止docker container


當使用

sudo docker container stop xxx 

卻發生 無法停止的錯誤

Error response from daemon: cannot stop container

可以透過

sudo aa-remove-unknown

之後就可以stop container

2020年10月12日 星期一

舊版本require-dir錯誤

在舊版本的gulp引用的require-dir(0.1.0)過舊

發生錯誤

TypeError: require.extensions.hasOwnProperty is not a function

if (!Object.prototype.hasOwnProperty.call(require.extensions, ext))

取代

if (!require.extensions.hasOwnProperty(ext))

即可正常運作

2020年9月25日 星期五

Redis 允許remote透過password連線

預設Redis Server以預設狀態運作

若需要載入指定的設定檔

需自行建立redis.conf

並以如

redis-server /usr/local/etc/redis/redis.conf 執行


redis.conf設定檔的內容為

bind 0.0.0.0 #允許remote連線

requirepass 12345 #設定連線密碼


測試是否設定正確可以使用redis-cli進行測試


1.安裝redis-cli工具

  sudo apt-get install redis-tools

2.要驗證是否允許remote連線成功 

  redis-cli -h 192.168.0.99 -p 6379

  透過redis-cli就可以連線進去

3.要驗證密碼的部份 則是要透過查詢才會知道

  192.168.0.99:6379> keys *

  (error) NOAUTH Authentication required.

4.確定會被要求密碼,以auth 輸入密碼

  192.168.0.99:6379> auth xxx

  OK



2020年9月15日 星期二

今天的幸福

每天上班沒有騎著平常習慣的路

特地繞了比較遠 到鼓山亭拜拜 坐坐

祈求全家平安 再進公司


忙了一整天 快下班時才接到PM任務

有程式問題要修改 明天要出貨給客戶

不想隔天再處理

先打電話回家 跟妹妹說 要加班晚點回去

打算改完再回家


有些複雜又有點久遠的程式碼

改好要回家已經快9點


騎車回家的路上 停等紅燈

身旁一個騎腳踏車的摩門教徒跟我說話

問我今天好不好

很直接的就回答說 不好

因為工作遇到困難 不過解決了

問我要怎樣才會好

我說 睡一覺就好了

...

路上電話又響了

妹妹:爸爸你什麼時候回來

我:爸爸在路上了,等一下就到家了


到家了

如平日一般 客廳燈已經關了

廚房燈還是亮著的

看到妹妹在餐桌上寫功課

妹妹:爸爸菜我幫你熱好了,你先吃飯

我:爸爸先洗澡 等一下吃

妹妹:不行 你先吃飯 不然冷掉了

我:好啦

坐著吃飯 妹妹邊寫功課邊跟我說起今天學校的事

洗好澡 上樓

叫妹妹早點睡覺

妹妹還是一直跟我說著話

我:妹妹 爸爸今天比較晚回來

  你還是要跟爸爸講這麼多話喔

妹妹:對呀

原本 覺得疲累 又悶的一天

卻是感到很幸福的一天


quasar q-table未顯示全部資料

使用案例在使用q-table顯示一個明細的列表

不做分頁 但資料卻只顯示部份

需要加上設定

:rows-per-page-options="[0]"

ex:

<q-table

  ...

  :rows-per-page-options="[0]"

>

2020年8月31日 星期一

Linux安裝VirtualBox

先說結論

1.到Linux Mint20(ubuntu 20.04)Virtualbox 只支援到6.0 請不要裝6.1

2.需要更改啟動 mok 


安裝VirtualBox

wget -q https://www.virtualbox.org/download/oracle_vbox_2016.asc -O- | sudo apt-key add -

echo "deb [arch=amd64] http://download.virtualbox.org/virtualbox/debian focal contrib" | sudo tee /etc/apt/sources.list.d/virtualbox.list

sudo apt update

sudo apt install -y virtualbox-6.0

sudo systemctl status vboxdrv

最後一步 如果成功 恭喜就可以省略下列步驟

但應該都會失敗


設定載入vboxdrv


1.安裝mokutil

sudo apt-get update

sudo apt-get upgrade

sudo apt-get install mokutil


2.註冊security boot密碼

openssl req -new -x509 -newkey rsa:2048 -keyout MOK.priv -outform DER -out MOK.der -nodes -days 36500 -subj "/CN=VirtualBox/"

sudo /usr/src/linux-headers-$(uname -r)/scripts/sign-file sha256 ./MOK.priv ./MOK.der $(modinfo -n vboxdrv)

sudo mokutil --import MOK.der

會要求設定密碼 用在 rebbot使用enroll mok輸入密碼時用

注意這個密碼只能使用一次

如果重新安裝virtualbox 需再重複此步驟重新設定密碼


3.重新開機

選擇 Enroll MOK/ Continue 到輸入密碼

輸入完密碼重新reboot即可

4.安裝vagrant

sudo apt update

curl -O https://releases.hashicorp.com/vagrant/2.2.6/vagrant_2.2.6_x86_64.deb

sudo apt install ./vagrant_2.2.6_x86_64.deb

參考連結

https://www.itzgeek.com/post/how-to-install-virtualbox-on-linux-mint-20/

https://askubuntu.com/questions/760671/could-not-load-vboxdrv-after-upgrade-to-ubuntu-16-04-and-i-want-to-keep-secur

2020年8月15日 星期六

nginx 使用return 與proxy_pass的差異

最近在做官網的移轉

舊的主機系統為Window的架構

新的主機則是Linux Docker架構

官網domain移轉後 原本有跑一些.net aspx的服務

就透過nginx轉回舊站上


轉回去是要用return 301 轉址還是用proxy_pass轉呢?

先說結論

如果是會經過瀏覽器顯示的網頁 使用return

如果是程式內執行的api使用proxy_pass

譬如說 www網站要移轉

我們把www給了新的主機, 舊的主機改用old 這網址

因此我們需要在新的主機上 把部分的www轉回old上


在新主機上使用return 網址上看到的網址會是old

如果程式內呼叫的api是透過return轉的

那麼程式內會先收到301 code而發生錯誤 而非你想像的

轉址後的api所產生的結果


而網頁的部分應該是透過browser呈現的

在收到 301 或307 都會自動轉到新的網址上

並不會出錯


在新主機上使用proxy_pass 看到的網址還是www 並不會因為內容是轉回old而顯示old

但是如果網頁的部分也使用proxy_pass 當然還是可以運作

但是每個連結就都會再經過新主機的nginx再轉過一次


另外透過proxy_pass 到old的domain上 是在主機內部運作

有可能發生不認得old這個domain 只要加上resolve dns就可以了

ex

location ~* .(php)$ {

  resolver 8.8.8.8 valid=30s;

  proxy_set_header Host $host;

  proxy_pass https://old.com$request_uri;

}


至於轉址的部分 透過$request_uri就可以取得host後面的完整網址

$args則是取得?後面的query參數

注意的是如果使用$request_uri 就不需要$args

ex: https://old.com/hello/me?name=oz&tel=123

$request_uri = /hello/me?name=oz&tel=123

$args = name=oz&tel=123


2020年8月9日 星期日

nginx 設定檔讀取與ansible安裝範例

在安裝好nginx 可以看到/etc/nginx下包含了
nginx.conf
conf.d/
sites-enabled/
sites-available/
幾個目錄
通常我們做異動修改的都會是sites-available/下
檢視一下幾個目錄之間的關係
nginx讀取的設定檔入口是nginx.conf檔案
可以看到包含了
include /etc/nginx/conf.d/*.conf;
include /etc/nginx/sites-enabled/*;
也就是說預設會去讀讀目錄是在sites-enabled
而在sites-enabled目錄下看到只有一個default的檔案

實際運作的方式
可以sites-available/ 下建立default.conf
然後把default.conf 做symblelink到sites-enabled/default
就可以
以 ansible做nginx的設定與安裝範例如下

---
- name: Install host nginx
  hosts: all
  become: yes
  tasks:
    - name: ensure nginx is at the latest version
      apt: name=nginx state=latest
    - name: start nginx
      service:
        name: nginx
        state: started
    - name: copy the nginx main config
      copy:
        src: ../../files/nginx/default.conf
        dest: /etc/nginx/sites-available/default.conf
    - name: remove old nginx conf
      file:
        path: /etc/nginx/sites-available/conf
        state: absent
    - name: copy conf folder to sites-available
      copy:
        src: ../../files/nginx/conf
        dest: /etc/nginx/sites-available
    - name: create symlink
      file:
        src: /etc/nginx/sites-available/default.conf
        dest: /etc/nginx/sites-enabled/default
        state: link
    - name: restart nginx
      service:
        name: nginx
        state: restarted

nginx 使用 rewrite return的差異

最近要將官網搬到另外一台主機上

但有些服務還是要回到原機器上

透過nginx的設定來達成預期目標

如果是method get 可以透過rewrite完成

ex:

server {
  server_name web.ozzysun.com
  location / {
      rewrite /api/send_get http://oldweb.ozzysun.com/api/send_get;
      rewrite /api/send_get2 http://oldweb.ozzysun.com/api/send_get2;
  }
}
如果要轉的url都是method:get 就可以在一個location內把要轉的都一起設定完
注意 只能對應get
如果是post的轉址 可以透過return去做
ex:
server {
  server_name web.ozzysun.com
  location /api/send_post {
      return 307 http://oldweb.ozzysun.com/api/send_post;
  }
}
但get可以透過return去轉嗎?
可以 但要把參數用$args帶過去
ex:

server {
  server_name web.ozzysun.com
  location /api/send_get {
      return 307 http://oldweb.ozzysun.com/api/send_get?$args;
  }
}
要注意的是rewrite真正的意義是
重整你的url 再交給下一個處理
當然 如果rewrite 有帶到http作用就跟return很像了

2020年8月8日 星期六

nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use

原本將nginx以docker部署

調整改成用ansible部署到主機上

安裝啟動一直發生錯誤

/etc/nginx目錄下的檔案不齊全

還有在/run/下找不到nginx.pid

報錯為

nginx: [emerg] bind() to 0.0.0.0:80 failed (98: Address already in use

這是個低級錯誤

就是80 port已經被佔用

乾淨移除nginx的部分

可以執行以下指令

sudo apt-get remove nginx nginx-common

sudo apt-get purge nginx nginx-common

sudo apt-get autoremove


查看是哪個程序佔用了80 port

netstat -anp |grep 80


查看才發現原本被停用 docker container nginx 在開機時被啟用

把80port佔住了 才發生在主機上無法安裝nginx的錯誤

停掉container 就一切正常了


2020年8月5日 星期三

vagrant 網路設定與ssh連線

當使用vagrant跑起vm後
要透過ssh進入vm內
預設可以使用vagrant ssh就可以直接連線
vagrant ssh指令的運作是
預設已經將vm的port 22 轉接上host的port 2222
vagrant ssh實際上就是連上127.0.0.1:2222

但如果要讓vm 可以讓host同一個lan裡面的其他機器可以連接到
也就是必須給vm 一個同區網的ip
可以在Vagrantfile加上設定指定ip
config.vm.network :public_network, ip: "192.168.0.88"
這樣就可以透過 標準的ssh 指令連線
至於連線要使用的private key在哪裏
vagrant預設會將key放在安裝目錄下的
.vagrant/machines/default/virtualbox/private_key
完整的ssh連線
ssh -i .vagrant/machines/default/virtualbox/private_key vagrant@192.168.0.88
就可以進去了

2020年7月28日 星期二

ansible安裝與 建立ssh連線

1.linux安裝
sudo apt-add-repository ppa:ansible/ansible
sudo apt-get update
sudo apt-get isntall ansible
測試 ansible --version

2.產生主控端ssh key
sshkey-gen
# 產生 ~/.ssh/id_rsa(private key) id_rsa.pub(public key)

3.複製主控端的id到遠端(被控端)
ssh-copy-id myuser@192.168.0.99
之後使用ssh myuser@192.168.0.9 就不需要輸入密碼

4.設定連線主機資資訊hosts.yml
all:
hosts:
  my-99:
    ansible_host: 192.168.0.99
    ansible_port: 22
    ansible_ssh_private_key_file: "~/.ssh./id_rsa" 
    ansible_user: myuser
    ansible_sudo_pass:

5.測試連線
ansible all -i hosts.yml -m ping
或
ansible my-99 -i hosts.yml

2020年7月24日 星期五

docker nginx container使用注意事項

通常使用nginx container 會將設定檔的部份
還有html的部份mount到主機host
方便異動檔案
以下是一些與平常使用nginx的差異注意的部份
1.upstream到本機host上的其他服務
原本的upstream server 設定只要設定
upstream myapi_srv{
  ip_hash;
  server localhost:12347;
}
當是使用container時
不要使用127.0.0.1或localhost這會是指到container內
需改為指到本機host所在的ip上
upstream api_srv01{
  ip_hash;
  server 192.168.0.195:12347;
}


2.alias設定檔案路徑
將host的myFlder目錄 mount到container下的/usr/share/nginx/html
-v ~/myFolder:/usr/share/nginx/html
原本alias到實體檔案所在位置 ~/myFolder/www
location /test {
  alias ~/myFolder/www;
}
nginx container則需改設定
location /test {
  alias /usr/share/nginx/html/www;
}

4.nginx.pid位置
pid檔的位置要查nginx.conf 內的設定路徑

2020年7月18日 星期六

長濱 小文家 日常

這次來長濱都住在小文家民宿
沒有之前住米粒教育家 或陌上草壎那樣的高級
但反而比較喜歡住在這裡像背包客的感覺
在長濱郵局斜對面的民宅
走出來就到長濱大街
再往下走 就是往海邊的方向
房間不大 但有冷氣有舒服的床
有洗衣機 每天在這裡都會把衣服洗好
對於很會流汗的中年男子 這是很重要的



每天早上起床 衣服放到洗衣機洗後
就走路到長濱大街上吃早餐
吃完早餐後 會在旁邊的巷子走走
走到吳神父的禮拜堂地方
跟送瓦斯的阿姨聊聊天
再回到小文家

今天晚上星空音樂會是這次來台東的主要目的
白天沒有安排活動
暑假 大姐的馨家小廚 客人很多
沒事大家就去店裡幫忙
開店前 我也只能幫忙檢檢菜
開店後 看著廚房裡大家忙的忙滿頭汗
我的功用大概就是幫忙送白飯 送湯

下午店休時間 去嘎嘎烏賴賴喝咖啡
嘎妞 一個台北的年輕人 來到台東來賣咖啡
之前都在大姐店門口擺攤
去年的海闊 也喝到他泡好喝的西西里咖啡
今年他們自己在烏鼻石租了個窩
有了自己的地方 來了 就想去那看看



烏鼻石 從長濱往南過了往玉長的入口不久後
海岸線 很容易看到突出於海岸延伸的黑色岩石地形 就到了
嘎嘎烏賴賴就在省道
一樣西西里咖啡 還有更令人驚豔的西西里冰沙
口感超棒
到這裡 不能錯過的是店後面的無敵海景

走出來 要回到車上 聽到的是很大聲原住民的歌聲合唱
循著歌聲 走過馬路 走進了烏鼻社區
看到正在進行著部落 年祭
這真是意外的收穫
沒有對外開放的年祭 外地人 除了我們大概也沒幾個

再回到長濱 已經是到開始用餐的時間
在店裡看到客人裡 看到了以莉高露 也算是意外

幫忙了一下 就出發去八仙洞的星空音樂會
選擇騎摩托車過去 因為不遠
傍晚騎著車在11號省道上奔馳 好像是年輕的時候才會做的事

到了八仙洞 打了卡 然後接到店裡的電話 停水了
我們又騎著車回店裡 爬上水塔檢查
也沒能做什麼處理 又再騎車到八仙洞

夜空下 音樂會剛開始
靠著山壁的草地上 大家都席地而坐
抬頭是滿天的星光
第一首曲子卡農 幾把提琴在夜色裡
音樂 星空 就是這麼美好
這樣難得的體驗 我想 會記得很久很久


2020年7月17日 星期五

瑞穗

這次 真正規劃要去的地方 只有瑞穗
起因 一次在電視上看到舞鶴地方的介紹
有機的茶葉烘培的蜜香紅茶 還有年輕人回鄉的咖啡經營
就想說有機會來這個地方看看
舞鶴就在瑞穗

長濱到瑞穗 一樣是走玉長公路再走9號
大概一個小時就到了
停靠在 東昇茶行
也算是自己第一次買茶的體驗
坐在店裡 各式的茶包 熱的冷的
喝了好幾輪
一坐就到快中午才離開

午餐去老家後山菜 也是在網路上找的
剛好有團客 所以出去繞了一下 一點才用餐
下午的行程只有安排去泡溫泉
中間的空檔 去了茶行老闆推薦的鳳梨社區
去吃了整顆鳳梨打的剉冰
從瑞穗開到富興社區的鳳梨公園 還是有段距離
不過開車在山裡的感覺 還蠻舒服的

泡完溫泉 開車回到長濱 也已經是傍晚的時間


2020年7月16日 星期四

今年長濱

雖然前一晚 一點多才睡
5點天剛亮就起床了

這個暑假要再開車去長濱
比較有計劃的在地圖上規劃了行程
怕雪隧塞車 6點就從台北開車 往宜蘭出發

有了幾次的經驗 由快速度道路接3號國道
再接5號國道 是最簡單不會手忙腳亂的走法
如預期的7點多就已經到了蘇澳休息站
打開google查 蘇澳的早餐
都是指向市區的美津早餐店
車開到現場 才發現今天並沒有營業
就簡單的在旁邊的豆漿店 吃了一下

去年夏天 來泡了蘇澳冷泉的滋味 一直念念不忘
查到的資料 蘇澳冷泉湯屋要到9點才開
空擋時間 先到南方澳觀景台
這時候的太陽 已經大的有些刺痛
拍了些照片 就離開


到蘇澳冷泉 才發現 原來夏天8點就開了
而且9點前進去還有優惠

雖然天氣很熱 冰冷的冷泉 要下去一開始是要一點勇氣的
當整個身子泡到池子內 毛細孔彷彿就發熱一般
慢慢的冰冷的感覺就不見了 然後看到手上腳上每根細毛上都結滿了小氣泡
還有從池底冒上來的溫泉花
半個鐘頭 起身 感覺相當的舒服

蘇花改 今年已經全部開通
全新台泥KADA園區是整個蘇花改的中間休息站
滿滿的人潮車潮 很難想像 這是個非假日的星期四

因為車上還載著幾箱冷凍食材要帶去長濱
離開台泥後 就沒再逗留 直接往台東開去

這次來民宿 就在長濱街上
走路就可以到大姐的店

晚上走在寂靜的長濱街道上
目的地只是路口的7-11
經過書粥 經過消防隊
我喜歡的旅遊方式 其實就是這樣
住在一個陌生的地方
穿著拖鞋 在街上晃
過著在地人的生活
也許這也是許多西部人 移居來長濱的原因吧





2020年7月15日 星期三

暑假開始了



早買好了上台北的高鐵
出門前一場大雨 叫不到可以上路的計程車
只好請小弟開車載我們出去
路上大塞車
還是轉到捷運站改搭捷運去高鐵
不是假日的週三早上 高鐵站滿滿都是人
我們還是一樣在摩斯吃早餐
每年寒暑假坐車前都在這裡

車窗外 雨還是持續的下著
過了台中 漸漸就是艷陽高照的好天氣

先在板橋放了妹妹的行李 再到新莊
幫妹妹配好眼鏡
走在幸福路上 朋友請吃了個義大利麵
再搭公車到西門町

到西門町的第一件事 先到阿宗麵線報到
非假日的時間來 不用排隊
雖然才剛吃飽飯 還是吃個幾口過過癮

這次帶妹來西門町 主要是來逛萬年
找看看有沒有他喜歡的公仔

西門町萬年是大學時常來買樂譜 逛街的地方
這裡的公仔小玩具飾品 都是他們這年紀喜歡的東西

就這樣我們在西門町的街道上來回的走了好多圈
累了 就找便利商店 坐著休息
傍晚再去台北地下街買了一隻公仔
才結束一天的行程
今天走的路也夠多了

晚上 再跟朋友到居酒屋 吃點東西
就回家休息 等一早起來
就要去長濱



2020年7月9日 星期四

quasar table在不同尺寸device 顯示不同欄位

不同於RWD操作div的顯示
如果資料以table呈現 但需要在小尺寸顯示比較少的欄位
可以用到 visible columns
標準以columns設定所有的顯示欄位
visible-columns的內容則是欄位名稱的array
如果有設定visible-columns prop
則真正顯示的欄位會是
columns內設定required:true的欄位+visibleColumns設定的欄位
要讓不同尺寸的device去顯示不同的欄位
只要在檢查尺寸的時候改變visible-columns的值即可

以下範例
在小尺寸的device上只會顯示 M_DAY(required:true所有的尺寸都必要顯示的)
與M_SMALL(來自visbleColumns設定的)

<template>
 <q-table
    :data="items"
    :columns="columns"
    :visible-columns="visibleColumns"
    ...
</template>
<script>
..
data () {
  return {
    items: [],
    columns: [ // 欄位宣告
      { name: 'M_DAY',
        required: true,
        label: '交易日期',
        field: 'T_DAY',
        
      },
      { name: 'M_TIME',
        label: '交易時間',
        field: 'T_TIME',
        format: (val, row) => moment(val, 'hhmm').format('hh:mm')
      },
      { name: 'M_SMALL',
        label: '交易時間',
        field: 'T_TIME',
        format: (val, row) => moment(val, 'hhmm').format('hh:mm')
      },...
    },
    visibleColumns: ['M_SMALL']
  }
}
created () {
  if (this.$q.screen.lt.sm) {
    this.visibleColumns = ['M_TIME']
  }
}
</script>

2020年6月30日 星期二

docker nginx 時間不同步

docker nginx 時間不同步
通常nginx上時區的設定只需要加上
autoindex_localtime on;
即可使用到local的timezone
但在container內是無效的
需要讓container與host也就是安裝docker本身的主機環境時間同步
可以在啟動時加上
v /etc/localtime:/etc/localtime:ro
完整的啟動指令範例如下
docker run --name=mynginx -d 
-v /etc/localtime:/etc/localtime:ro 
-v ~/myhtmlfolder:/usr/share/nginx/html 
-v ~/docker_share/nginx/conf:/etc/nginx/conf.d
-v ~/docker_share/nginx/nginx.conf:/etc/nginx/nginx.conf:ro 
-v ~/docker_share/nginx/logs:/var/log/nginx 
-p 80:80 nginx

mac上時區設定localtime無效須改用時區設定

docker run --name=mynginx -d 
-e "TZ=Asia/Taipei" 
-v ~/docker_share/nginx/nginx.conf:/etc/nginx/nginx.conf:ro 
-v ~/bcc:/usr/share/nginx/html 
-v ~/docker_share/nginx/conf:/etc/nginx/conf.d
-v ~/docker_share/nginx/nginx.conf:/etc/nginx/nginx.conf:ro
-v ~/docker_share/nginx/logs:/var/log/nginx -p 80:80 nginx

2020年6月17日 星期三

sequelize 無pk執行刪除destroy

通常執行刪除 條件必需要帶有table所定義的pk欄位
如果沒有會無法執行
但當需要以特定的條件執行刪除
但又未包含pk欄位時
可透過設定individualHooks=true
此時sequelize會先執行select 再刪除select取得的rows
這樣就可以達到未帶pk執行刪除的功能
ex
model.destroy({
  where: { xxxxx },
  individualHooks: true
})

2020年6月5日 星期五

netplan網路設定

使用netplan設定可以避免設定錯誤無法連線主機的狀況
設定檔案
/etc/netplan/xxx.yml檔案
範例檔案
network:
  ethernets:
    enp4s0:
      addresses: [192.168.0.99/24] // 設定固定內部固定ip
      gateway4: 192.168.0.254 // 設定gateway
      dhcp4: no //設定不用dhcp
      nameservers: //設定使用的dns
        addresses:
          - 8.8.8.8
          - 8.8.4.4
          - 168.95.1.1
  version: 2
不知道gateway在哪裡 可以用
ip r | grep ^def

設定完用
sudo netplan try
測試 如果ok 使用
sudo netplan apply
寫入
如果try之後 在2分鐘內沒有apply
設定值會恢復原來的

2020年6月1日 星期一

巴奈 泥娃娃20年

耳機裡 聽著馬芳這一集的耳朵借我
巴奈泥娃娃專輯20年
這張最喜歡的唱片
經過了這20年
聽著巴奈流浪記 眼淚還是會滑落下來

2000年還在康軒上班的日子
那是還在聽著CD 隨身聽的年代
週六到公司加班 空蕩蕩的辦公室只有自己一個人
反覆的聽著泥娃娃專輯
放下手上的工作
沉浸在滿滿的音樂情緒當中


2020年5月27日 星期三

Sequelize 作subquery 範例

orm作單一table查詢 若需要查詢的條件需引用自子查詢
以下是簡單的範例
sql作法

select * from maintable where uid in(select uid from uidTable where flag='Y')
以sequelize model執行方式
mainTableModel.findAll(
  {
    where:{
      uid: {
        [Op.in]: [sequelize.literal(`(select name, uid from maintable where uid in(select uid from uidTable where flag='Y')`)]
      }
    }
  }
)

2020年5月26日 星期二

Linux log journal清除

Linux log檔案放在/var/log下
查log佔的容量
sudo du -sh 
發現 /var/log/journal內佔最多的容量

sudo journalctl --vacuum-size=10M

讓jounnal只保留10m
參考來源
https://blog.csdn.net/sunboy_2050/article/details/89530790

2020年5月24日 星期日

徒步 高雄四維路

一直很喜歡以徒步的方式在都市裡旅行
徒步看到的風景 跟騎車是截然不同的視野
走過才會記得沿路的風景
以前總在國外才會進行的方式
想想 對於自己所居住的地方
也可以用這樣的方式 去看看

四維路的東邊這端
從河南河北路切入四維路
不過是大概兩個車道的道路
到了凱旋才比較寬闊起來
廣州街文化中心一帶 林立的店家
這一帶 舊名林德官
很多賣吃的老店 都是平常騎車不會注意到的
好吃的金龍水煎餃 每回走過 總會停下來吃個幾顆再走

光華到中山之間的四維路
寬闊的林蔭行人道 是四維路最舒服的一段
因為是走路 所以對於紅綠燈的秒數 總特別敏感
靠近復華中學的明權路口
大概有至少8個車道寬 卻只有30秒的時間
每次都不需要小跑步過馬路才來的及
而像仁愛街口那樣 大概走不超過20步就可過的馬路
竟然有90秒的時間 很不解紅綠燈秒數是如何設計
早到快接近中山路口
可以看到路人咖啡就在這裏
再往前穿過了中華路 穿過了自強路
四維公園旁鄰近的苓雅市場
鼓山亭 大概就是我步行的終點
在這裡點個香拜拜 坐一下
再回家
時間還夠 可以步行返回
騎公共腳踏車 回程也是不錯的選擇






2020年5月20日 星期三

nodejs上RabbitMQ 使用amqplib 紀錄

在nodejs上實作rabbitMQ的client端
使用amqplib module
依照文件做一些紀錄

Overview
  1.在與RabbitMQ建立連線connection後
    在connection上是可以建立多個channel
  2.RPC端透過AMQP與Server連接 都是透過非同步的方式的溝通
    也就是說 RPC不是直接與RPC溝通 而是透過中介的RabbitMQ Server
    傳送與接收
    因此大多數amqplib提供的操作method 並不會由server取得回應
    或只是接收到boolean的回傳值
Dealing with failure
  大多數AMQP的操作,只要沒達到預期的狀態就會當作錯誤
  因為錯誤可能造成channel關閉,錯誤發生或可能產生的效應
  1.目前發生錯誤的RPC會被reject
  2.使用的channel物件會因為錯誤 造成之後的操作發生問題
  3.任何等待傳送的RPC 都會被reject
  4.造成channel物件emit 'error'
  5.造成channel物件emit 'close'
  當channel發生錯誤有可能是其他的RPC所造成
  而非當下連線的RPC造成
  要去找到問題發生原因可以透過
  try catch捕捉到錯誤e的stackAtStateChange會是有用的錯誤資訊
connection.createChannel().then(function(ch) {
  ch.close();
  try {
    ch.close();
  }
  catch (alreadyClosed) {
    console.log(alreadyClosed.stackAtStateChange);
  }
});

Flow Control
channel的運作會類似於stream.Writable
  1.當呼叫publish或sendToQueue時會回傳
    true:代表 'keep sending'
    false:代表 please wait for a 'drain' event
  2.呼叫以下這些method則不會有任何server的回傳
    包括ack, ackAll, nack, nackAll, and reject
  3.ConfirmChannel則會以callback來接收boolean值
    當server有確認了message時 callback會被呼叫

Argument handling
  許多的method操作都會吃一個option參數
  option本身有一些預設的option參數值
  如果傳入非option定義的參數內容會被忽略
  通常會把option合併成一個單一物件便於使用
var common_options = {durable: true, noAck: true};

var bar_opts = Object.create(common_options);
bar_opts.autoDelete = true;

var foo_consume_opts = Object.create(common_options);
// 使用arguments table方式priority,必須以x-格式寫, 
foo_consume_opts.arguments = {'x-priority': 10};

var bar_consume_opts = Object.create(foo_consume_opts);
// 覆寫之前已經設定的prooprity值
bar_consume_opts.priority = 5;

Field table values
  在publish與sendToQueue的option內
  包括arguments與headers都是 field table值
  都是key-value object型式
  有一些特別的value型態會在table內被encode
  當js內會以!語法來標明其型態
ex:
  {'!': 'int8', value: 64}
  {'!': 'decimal', value: {digits: 4999, places: 2}}

2020年5月15日 星期五

RabbitMQ noAck設定

當接收者設定監聽訊息時 可以設定是否要回應MQ

noAck:true 表不需做任何確認
也就是說MQ將訊息送給consumer(接收者)後
就會立刻把這筆訊息由queue清掉

預設noAck為false
當producer送出訊息到MQ上
MQ將會通知有設定監聽的consumer
接收端在設定接聽時可以透過noAck設定是否必須要回應MQ
noAck:fasle 表一定要回應讓MQ知道工作已完成
若沒有回應,則訊息還在MQ內並不會被清除
下次還是會再重送
consumer的確認動作
只要執行channel.ack(msg)就可以了
注意 這裡的msg是由mq送過來的訊息物件
不要做任何修改 直接當作ack的參數

當接收者不在線上
sender發出後
當接收者後來才上線
無論noAck設定為何都會收到

2020年4月28日 星期二

fcm 推播 icon必須是只有白色

測試FCm推播
踩到一個雷點 分享一下
android 7之後(包括7)
推播notify icon必須是只有白色
用原本的icon都會變一片空白
以下網址可以驗證並產生推播用的icon
http://romannurik.github.io/AndroidAssetStudio/icons-notification.html#source.type=image&source.space.trim=1&source.space.pad=0&name=fcm_push_icon

在 AndroidManifest.xml的applications內加入
使用fcm icon 設定
<meta-data android:name="com.google.firebase.messaging.default_notification_icon" android:resource="@drawable/fcm_push_icon" />

其中fcm_push_icon是存在於res/draw-xxx/ 各目錄下icon檔案名稱

2020年4月24日 星期五

git 查詢commit 紀錄

今天遇到一個曾經遇過的問題
但已經忘記之前是怎麼解決
一個維護較長時間的專案 往往有一堆的commit
要從過去的commit紀錄內爬到自己要找的那個commit
當然不可能一個個去翻
透過指令 是最好的方法
git log --all --grep='htc'

安裝與設定使用 nginx docker

利用nginx docker取代在系統內安裝的nginx
1.基本docker指令

docker images 察看本機已下載的image
docker container list 察看本機上已經建立的container
docker ps 列出正在運行的container
docker stop containerID 停止container運作
docker container rm containerId 刪除container
docker image rm imageName 刪除image

2.初始安裝nginx
docker run --name=mynginx nginx -p 3838:80
  以nginx這個image安裝 命名為mynginx的container
  並將docker內部的80 port 對應到外部(host)使用的3838 port
  若本機並不存在nginx image會自動由網路下載安裝

3.進入nginx container 察看目錄
docker exec -it mynginx bash
  進入container 內察看設定檔的目錄準備用來對應到本機目錄使用
  查到nginx目錄在container內的
  /etc/nginx
  www根目錄在
  /usr/share/nginx/html

4.將nginx 設定檔與html目錄對應到本機上
  在本機上建立目錄用來對應
  ~/docker_share/nginx/html 對應html目錄
  ~/docker_share/nginx/conf 對應nginx設定檔
  設定nginx.conf單一檔案的對應需要使用:ro readyonly模式
  重新建立 container
docker run --name=mynginx -d -v ~/docker_share/nginx/html:/usr/share/nginx/html 
  -v ~/docker_share/nginx/conf:/etc/nginx/conf.d -v ~/docker_share/nginx/nginx.conf:/etc/nginx/nginx.conf:ro
  -p 3388:80 nginx
  若原container已存在可停止刪除再安裝

5.重啟nginx
  重啟nginx 的指令為 nginx -s reload
  可透過exec指令執行container內部指令
docker exec -d mynginx nginx -s reload
  當然也可以透過
  docker exec -it mynginx bash 直接開shell進入container
  再執行
  nginx -s reload


2020年4月10日 星期五

nightwatch chromeDriver版本問題

vue-cli 預設的e2e測試為nightwatch
使用vue-cli預設不用設定即可跑起e2e測試
如果遇到以下錯誤訊息
Error: An error occurred while retrieving a new session: “session not created: This version of ChromeDriver only supports Chrome version 77”

來自測試安裝的chromeDriver與現在自己機器上的Chrome版本不相符
vue-cli預設安裝nightwatch帶的chromeDriver為77
查一下機器上跑的Chrome版本為80.x
只要重新安裝
npm install chromeDriver@80 --save-dev
即可正常運作

2020年4月2日 星期四

quasar table 取server資料 分頁使用

1.元件設定
  1.rows-per-page-options:設定option供選擇每頁顯示幾筆(對應rowsPerPage)
  2.pagination: 對應分頁設定
  3.@request:當在分頁物件上按上下頁或是切換每頁顯示幾筆都會被觸發的handler
    handler接收到的參數props並非現在物件上的pagination設定值
    而是要變成的pagination
<q-table
  :data="items"
  :rows-per-page-options="[50,100]"
  :pagination.sync="pagination"
  @request="onRequest"
>
2.script
  1.設定pagination物件
    page: 目前第幾頁 要操作載下一頁 需要將第幾頁更新回這裡
    rowsPerPage: 每頁幾筆,當在元件操作切換要顯示的數量,要寫回這裡
    rowsNumber: 總筆數,這要由server取得的資料來更新
  2.doQuery真正執行server查詢的function
    在執行真正查詢所需要的分頁參數 ex取第二頁資料
    這些值都是由pagination設定值拿來當作參數
    pagination設定值會因為元件的操作而動態變化
  3.設定的onRequest handler
    當在分頁物件上按上下頁或是切換每頁顯示幾筆都會被觸發的handler
    handler接收到的參數props並非現在物件上的pagination設定值
    而是要變成的pagination
    要將取得的資料寫回pagination 再執行查詢
    執行查詢的doQuery會去讀取pagination內的資料來執行
data() {
  return {
    pagination: {
      items: [], // table要顯示的資料
      page: 1, // 目前第幾頁
      rowsPerPage: 50, // 每頁幾筆
      rowsNumber: 20 // 總筆數
    }
  }
}
methods: {
  async onRequest (props) {
    const { page, rowsPerPage } = props.pagination
    this.pagination.page = page
    this.pagination.rowsPerPage = rowsPerPage
    await this.doQuery()
  },
  async doQuery () {
    // 將pagination內的分頁資料 設定到api所需要吃的參數
    const queryParams = {
      countPerPage: this.pagination.rowsPerPage
      currentPage: this.pagination.page
    }
    // 假設呼叫api 吃queryParams參數執行server query
    const response = await doAPIfetch(queryParams)
    // 假設api回傳 data(查詢結果) 與meta(包含分頁資料)
    this.items = response.data
    this.meta = response.meta
    // 將分頁資訊取得的資料總量寫回pagination.rowsNumber
    this.pagination.rowsNumber = this.meta.total
  }
}

2020年3月31日 星期二

axios 加上before after處理

使用axios如果需要在
request送出前 加工送出去的資料
或接收到response後 加工收到的結果
可以使用這樣的結構去攔截修改
1.建立request物件
2.送出request前加工送出資料
  可以加入header或調整送出內容
3.接收到api回應後 做資料整理

const myRequest = axios.create({
  ...
})
myRequest.interceptors.request.use(config => {
  // 修改config內容 就是
  config.headers[xxx] = xxxx //加上header
  return config
})
myRequest.interceptors.response.use(
  response => {
    .... // 自行處理
    return response 
})
例如axios送出資料
需要以x-www-form-urlencoded 格式送出
除了需要加上content-type設定外
還需要在送出去之前 對於資料先做轉換(需另外用qs處理)
import Qs from 'qs'
myRequest.request.use(config => {
  config.data = Qs.stringify(config.data)
  return config
})

2020年3月27日 星期五

Klima - Fluorescent Stars

假日裡 當所有的人在酒吧裡狂歡
我只想一個人靜靜的躺在床上
閉上眼 數著一個 又一個 滿天的星星


小時候 躺在床上睡覺
眼睛盯著天花板
在天花板上 貼上螢光貼紙
黑暗中 一點點的亮光 總讓人可以進入彷彿
浩瀚 未知的世界
從沒想過 可以貼滿整面的牆
讓螢光的黃色星光 閃爍在黑暗中
這是遙遠的想像

Klima的專輯 已經在電腦裡躺了很久
打開才發現自己錯過了這個聲音好久

Fluorescent Stars

It's saturday night
And i don't want to go out
I'm staying in bed
Watching the stars on my wall
My friends are in a bar
Drinking beers and telling jokes
I'm here on my own
Counting the stars
So many of them
My eyes are closing
So many of them
One, two, three, four hundred
The noise from the street
Is coming to my ears
But they've decided to be deaf tonight
And concentrate on the stars
So many of them
My eyes are closing
So many of them
One, two, three four hundred

2020年3月21日 星期六

dart專案建立與基本指令使用

1.dart安裝與環境設定
  透過dart官網說明即可順利安裝dart sdk
  https://dart.dev/get-dart
  dart也有像npm一般可以取得其他網路上open的package的地方
  https://pub.dev/
2.環境設定
  pub指令相當於node的npm指令 用來安裝或執行
  dart 安裝好即包含了pub指令 就如同node安裝好也會帶有npm一樣
  但需要設定路徑到系統內可以確保指令可以被認得
  mac因為是透過homebrew安裝dart 所以不需要特別設定就可使用
  linux需要設定在rc檔案內(ex: .bashrc或 zshrc)加入路徑
export PATH="$PATH:/usr/lib/dart/bin"
export PATH="$PATH":"$HOME/.pub-cache/bin"
3.建立專案
  dart 本身提供可以建立預設專案模板的工具stagehand
  我們需要先透過pub指令來安裝stagehand
  之後就可以透過stagehand來產生各種預設的專案目錄
pub global activate stagehand // 安裝stagehand
stagehand // 列出可用的樣本
stagehand // ex: stagehand console-simple 產生樣板
  目錄下pubsepc.yaml為專案的設定檔案包含專案內需要使用的package都寫在這裡
  注意:要先產生目錄 在目錄內執行 產生樣板的指令
4.pub指令
  pub與npm的差異是透過pub global安裝package會將package統一存放在
  .pub-cache目錄下 再提供各專案使用
1.pub global activate: 由網路上安裝新的package 會安裝到 .pub-cache/global_packages下
2.pub global list: 列出已經安裝可以使用的pacckage
3.pub get: 如果目錄下已經有pubsepc.yaml設定檔案 會依照設定安裝package
4.pub upgrade: 將目錄下pubsepc.yaml已經設定的package 升級
5.pub downgrade: 反過來做package降級
6.pub run 執行指定的檔案
   ex: pub run bin/main  等同執行  dart bin/main.dart
  參考https://dart.dev/tools/pub/cmd
5.dart與node 對照
dart ==== node
pub  ==== npm
pubsepc.yaml === package.json
pub get=== npm install

2020年3月6日 星期五

android 無線adb連接設定

很久就有的功能了
最近用到 記錄一下
在做android app測試 需要直接deploy到實體機器上
通常都會需要使用usb線連到工作電腦上
在device上開啟開發者模式
就可以在電腦上透過adb devices檢查是否有連上設備
有看到就可以直接deploy app到設備上

也可以透過區域網路以無線的方式連接
不過在設定上還是需要先透過usb線連上
再設定
以下紀錄連線的流程
1.將手機使用usb線連接電腦
2.adb tcpip 12345
  設定以手機以12345 port與電腦連接
3.拔除usb線
4.查看手機目前wifi取得的ip(ex:192.168.0.9)
5.電腦 adb connect 192.168.0.9:12345
  連線
6.再用adb devices檢查
  就可以看到有一個 192.168.0.9:12345的device
7.恢復改用usb
  adb usb 就可以了
這時候就可以如同接上usb線一般做各種測試
或透過chrome inspect查看手機內應用程式的狀況

2020年2月18日 星期二

賽璐璐-2001華山野台

曾經兩次聽過賽璐璐的現場
印象 其實並不是很好
一次在華山的野台開唱
一次在河岸
兩次都是因為PA做的不好
聲音都混雜的聽不出細節

這張唱片 買了很久
最喜歡的曲目是Em 前奏那大篇幅的吉他
聽過就不會忘記
不過到這幾年才慢慢把這張唱片聽出味道

題外話
那年的2001野台在華山 大概是聽過最瘋狂的一場

戶外的場地 只記得聽到了剛發第一張專輯的董事長
還有四分衛
因為颱風來襲 後來表演都在室內
那時候的華山室內表演的場地
還相當簡陋的像工地一樣
初次的賽璐璐的表演就是在這裡聽到
會來野台 大家應該都是來衝 MegaDeath
因為颱風 到凌晨四點才開唱
等結束要回家都已經天亮了
年輕才有這樣的氣力吧

2020年2月5日 星期三

六叔

過年前的一通電話
六嬸打電話來 說六叔要出院
是不是有時間去幫忙
找了大弟 一起開車過去
醫院裡 六叔虛弱的樣子 已經跟過去差很多
開著車 回到家

老舊的公寓 六嬸準備了一張塑膠椅 把手綁上了毛巾
跟大弟 也是花了些力氣才將叔叔抬到家裡
要走時 六叔拉著我們兄弟兩 坐下
跟我們說話 離開時握著他的手
這也是 他生前最後握到他的手
大年初四接到電話 六叔走了
想想 在他最後 心裏有還想到我們去帶他回家過年
也是一件圓滿的事

爸爸的兄弟很多
六叔是較親近的叔叔
記憶中 剛上國中 六叔來家裡 教我英文
十幾年前 在台北
在那個我要決定人生大事的時刻
六叔六嬸帶著我媽到台北來看我
許多的事 就這樣一直牢記在我心裡



2020年1月14日 星期二

冷水坑 一遊

陽明山 除了國中畢業旅行來台北有上去外
在台北住了10幾年大概也只去過一次

要上班的禮拜二 8點50分的高鐵上
除了要去台北開會上班的上班族
大多是上了年紀悠閒生活的長輩

出了板橋車站 馬路上看起來剛下了一點雨
往新莊的99號公車 少了趕上班趕上課的學生
這是平日休假可以享受到的輕鬆

看著窗外 過了大漢橋 一站一站
下車在中華路與幸福路口
沿著幸福路 慢慢的走 轉過了中平路
再走到麥當勞
點了個早餐
才吃完 你就出現了
滿臉笑意的你 我知道你現在心情不錯

開著車 上陽明山 本來說去擎天岡看看
山上霧濃 到冷水坑已經看不到再往上的路
四處霧茫茫的一片 看不到更遠的地方
往夢幻湖的路上 公共澡堂外
許多上了年紀的阿公阿嬤 在這裡泡腳
繼續往上走 雖說 指標只是大概一公里的路程
全部都是上坡路 還是要停下來休息一下
路上 已經有許多櫻花開了
想起了 踏浪歌詞的那段

山上的山花兒開啊 我才到山上來
原來你也是上山 看那山花開

夢幻湖到了 好像不太夢幻
不過要的是一起走這段路的過程
終點 其實 不是重點

要下山了 也到冷水坑泡泡腳
不過水溫 太低 沒有泡溫泉的舒服
開著車往北投 泡真正的溫泉