こんにちは。kaoruです。
今回は、localStorage使って「1日以上前に取得した天気予報」を保持しておき、表示する機能を実装してみました。
最近は天気が変わりやすいので「以前調べた時は来週月曜は晴れだったかな?」など知りたい時があるかもしれません。
…ないかもしれませんが、localStorage実装を追加する過程で色々学びがありましたね。
【前回】react-router-domでルーティング (Wheather-app実装 7)
localStorage実装
localStorageって?
ブラウザに情報を保存しておく機能です。
Cookieと異なるのはサーバに送らない、という点ですね。
保存しておけるのはString(文字列)だけです。
JSONなどを保存したい場合は文字列にシリアライズしてから等、加工が必要ですね。
localStorageを使う際の注意点
localStorageはJSからアクセスできてしまうので、個人情報やパスワードなど機密情報を保持することは避けましょう。
また、localStorageへのアクセスは同期処理になる(非同期ではない)のでパフォーマンスに注意しましょう。
localStorageは消さない限り残り続けるので、明示的に消す必要があります。
localStorageの使い方
localStorageへ情報を保存
例)localStorageに”foo”という名前で”bar”という値を保存
以下のどちらか
- window.localStorage.foo=”bar”;
- window.localStorage.setItem(“foo” , “bar”);
localStorageから情報を取り出す
- const item = window.localStorage.getItem(“foo”)
localStorageを使って「前回取得した天気予報」を表示する
- 「前回取得した日付」をlocalStorageに保存する
- 「前回取得した天気予報情報」をlocalStorageに保存する
- 「前回取得した日付」をlocalStorageから取り出す
- 「前回取得した日付」が今日から1日以上過去の場合、「前回取得した天気予報情報」をlocalStorageから取り出す
- 「前回取得した天気予報情報」が取り出せた場合、画面下部へ「前回取得した天気予報情報」を表示する
処理の流れは、上記の通りです。
これをReact Hooksで実装します。
ポイントとしては以下がありました。
- 「前回の天気予報表示する判定結果」「前回取得した天気予報情報」をinitialStateに追加する
- useEffect()を使って初回だけ今回の追加処理が走るようにする
「前回取得した日付」「前回取得した天気予報情報」をinitialStateに追加する
画面上のステータスはuseReducerで変更できるようにStateに追加です。
「前回取得した日付」はlocalStorageで扱っていますがStateには入れません。
Reactコンポーネントとしては「前回の天気予報表示する判定結果」だけあればいいからです。
Stateに追加しましたので、変更を当然Reducerにも追加します。
Stateの変更はReducerで行うことを一貫しておけば、後から変更処理を追いかける際にdispatchだけを探せば良くなりますね。
useEffect()を使って初回だけ今回の追加処理が走るようにする
コンポーネントレンダリングの初回だけ前回天気予報の表示処理を動かします。
前回かどうかの判定を[1日以上]としているので初回だけでいいかな、と思います。
useEffect()を実装で使ってみたくて採用しましたが、useMemo()でも良かったかもしれません。
実装過程での学び、つまづいた所
Flexbox flex-direction:columnで左右中央寄せ
justify-content: centerで、、出来ないのです!
flex-direction: row;(横並び) であれば問題ないのです。
flex-direction: column;(縦並び) の場合は、align-items: center;で左右中央寄せになるみたいです。
JavaScriptでの日付取得
現在日付+時間は date = new Date()で拾えます。
そこからの加工だったり比較だったりがそこそこ自分で実装しないとダメでした。。
- date.getMonth() の結果は数値(0~11) ※なぜか1月が0始まり
条件付きレンダー
ある条件の時だけ該当情報を描画したい場合です。
今回でいえば「前回の天気予報を表示する判定結果」がTrueの時だけ前回天気予報を表示したいです。
{}中に三項演算子を使うことで実現できます。
return(
{ hoge > 1 ? <ComponentA /> : <ComponentB /> }
)
React公式によると「論理 && 演算子」でも条件が付けられるとのことです。
aタグのセキュリティ対策
target=”_blank”をつける場合は、 rel=”noopener noreferrer”を付けましょう
TypeScript型定義でnull可能性も書く
処理の中でnullが入る可能性がある場合はnullも型定義に入れておかないとエラーになりますね。
const hoge: string[] | null[] = funcA()
まとめ
localStorageは簡単にかける。でもStringだけなので加工が少し必要。
コンポーネントで扱うステータスが増えたらState/Reducerにちゃんと組み込むの大事。
レンダリングなどライフサイクルのイメージが少しできてきた。
では、また〜。
コメント