20201017のReactに関する記事は4件です。

firebaseでpull request ごとにpreviewをdeployするgithub action

概要

firebaseで、spaをnetlify やvercel のようにプルリクごとにURLを変えてdeployしたい。

how to

firebaseの初期化

公式
firebase toolをグローバルにinstall
今回はdeployする directoryはdistをしていします。(firebaseのdefaultはpublic)

npm i -g firebase-tools
firebase login
firebase hosting #deloyするdirectoryをdist にする

channel deployコマンドをpackage.jsonに追加

previewようのdeployはchannel deployというコマンド使います。
そのため、以下のように scriptに追加します。


{
  "name": "firebase deploy app",
  "version": "1.0.0",
  "private": true,
  "scripts": {
    "dev": "nuxt-ts",
    "build": "nuxt-ts build",
    "start": "nuxt-ts start",
    "generate": "nuxt-ts generate",
    "lint:js": "eslint --ext .js,.vue --ignore-path .gitignore .",
    "lint:style": "stylelint **/*.{vue,css} --ignore-path .gitignore",
    "lint": "yarn lint:js && yarn lint:style",
    "test": "jest",
    "channel-deploy": "firebase hosting:channel:deploy" ←# 追加
  },

github workflowを設定する

以下のように設定します。

firebase-deploy.yml
name: CI

on: [push]

jobs:
  FrontDeploy:
    name: FrontDeploy
    runs-on: ubuntu-latest
    steps:
    - name: Checkout Repo
      uses: actions/checkout@main
    - name: setup Node
      uses: actions/setup-node@v1
      with:
        node-version: '12'
        registry-url: 'https://registry.npmjs.org'
    - name: Install Dependencies
      run: yarn
    - name: Build
      run: yarn build
    - name: deploy to Firebase Hosting
      shell: bash
      run:  yarn channel-deploy $(echo ${GITHUB_REF#refs/heads/}) --token=${{ secrets.FIREBASE_TOKEN }}

こちらでは、branch名を取得しています。

$(echo ${GITHUB_REF#refs/heads/})

tokenを取得

以下コマンドで、tokenを取得できます

firebase login:ci

取得したtokenをFIREBASE_TOKEN にいれましょう。

Secrets.png

以上でdeployできるはずです!

twitterもフォローよろしくおねがいします。 !

https://twitter.com/yoshixj

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【React Native + Expo】React Hook Formでバリデーションを簡易実装してみる

React Hook Formはフォームバリデーションをシンプルかつ簡単に記述できる便利なライブラリです。
FormikやRedux Formなどバリデーションに関してのライブラリは他にもありますが、
パフォーマンスの良さや記述量の少なさからこちらのライブラリを使うと実装が楽になるのでオススメです。

ReactNativeに関しては以下のURLにクイックスタートがかかれているので、参考にしてみてください。
https://react-hook-form.com/jp/get-started#ReactNative

React Nativeの注意点

ReactNativeのサポートはしっかりとされていますので、使うことはできます。
ただし注意点としては、Reactと同様のAPIが使えない部分があるとのこと。

React Native と互換性のない API がいくつかあります (Web とネイティブとの API の違い)。

また、書き方についても手動登録 (manual register)が必要とのこと。。。
とにかくソースコードを確認してみましょう。

ソースコード

import { useForm, Controller } from 'react-hook-form';
  const { register, control, handleSubmit, errors } = useForm();
  const onSubmit = (data) => console.log(data);
     <Controller
        control={control}
        render={({ onChange, onBlur, value }) => (
          <TextInput
            onBlur={onBlur}
            onChangeText={value => onChange(value)}
            value={value}
          />
        )}
        name="firstName"
        rules={{ required: "入力が必要です。" }}
        defaultValue=""
      />
      {errors.firstName && <Text>{errors.firstName.message}</Text>} 

該当ソースコードは以上で、だいぶスッキリと書ける印象です。

補足

Controller

      <Controller
        control={control}
        render={({ onChange, onBlur, value }) => (
          <TextInput />
        )}
        name="firstName"
        rules={{ required: "入力が必要です。" }}
        defaultValue=""
      />

先程の「手動登録 (manual register)が必要」というのはController内にあるrulesにあたる箇所になります。
そもそも、registerとはバリデーションルールを設定するためのもので、useForm内でも定義することができます。

errors

 {errors.firstName && <Text>{errors.firstName.message}</Text>} 

バリデーションエラ-の内容はuseFormで定義されているerrorsを呼び出すことで確認できます。
上記のソースコードでのerrorの内容は、Controller内にあるrulesに定義した「入力が必要です。」が出力されます。

実装例

終わりに

今回紹介した内容は一部分だけですので、APIリファレンスを読んで書き換えたりすると理解が深まるかと思います。
また。実装で必要なバリデーションルールに沿ったものが、作れるのかを試してみようと思うので
詳細な作りに関してはまた別の記事で書こうかと思います。

まだ、まとめきれていない部分が多々あるので、実装方法としてこうしたほうが良いとか間違いがあれば教えていただくと嬉しいです。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【React】 合成イベント(SyntheticEvent) を利用する時注意点

Reactの合成イベント(SyntheticEvent )特性

  1. ブラウザのイベントハンドラーとReactのSyntheticEvent は別である
  2. SyntheticEventはPullingされる。
  3. SyntheticEvent再使用される。
  4. 全ての属性は呼び出し後に初期化される。

実際にエラーを作てみましょう

export default function App() {
  const syntheticEvent = (event) => { // 1.全ての属性は呼び出し後に初期化される。

    setTimeout(() => {. 
      console.log(event.target.value); //2. 非同期でevent.target.valueを呼ぶと警告が発生する!!
    }, 1000);
  };

  return (
    <div className="App">
      <input type="text" onChange={syntheticEvent} />
    </div>
  );
}

警告発生

Warning: This synthetic event is reused for performance reasons. If you're seeing this, you're accessing the property >target on a released/nullified synthetic event. This is set to null. If you must keep the original synthetic event >around, use event.persist(). See https://fb.me/react-event-pooling for more information.

解決方法

1. event.persist()を追加する
export default function App() {
  const syntheticEvent = (event) => { 
     event.persist() // 1. 警告が書いているメソッドを追加 
    setTimeout(() => {
      console.log(event.target.value);
    }, 1000);
  };

  return (
    <div className="App">
      <input type="text" onChange={syntheticEvent} />
    </div>
  );
}

補足
非同期処理の中でイベントのプロパティにアクセスしたい場合は、event.persist() をイベント> 内で呼び出す必要があります。これにより、合成イベントがイベントプールの対象から除外され、イベントへの参照をコードで保持できるようになります。

上のreactドキュメントはevent.persist()を利用する場合。
①. 合成イベントがイベントプールから除外される。
②. ①の理由で呼び出し後に初期化されない。
③. ②の理由で非同期の内部でもevet.target.valueの値が利用できる

event.persist()を利用する事は上の①の理由でオススメしない。

2. event.target.valueの値をPrimitive(プリミティブ)値で取得

export default function App() {
  const syntheticEvent = (event) => { 
    const value = event.target.value // 1.primitive値で取得 
    setTimeout(() => {
      console.log(value);  //2.警告は発生しない値を表示
    }, 1000);
  };

  return (
    <div className="App">
      <input type="text" onChange={syntheticEvent} />
    </div>
  );
}

この方法でする事をオススメします。
合成イヴェントを除外しなくても利用できます。

結論

Reactの合成イベントを利用する時は非同期処理について注意が必要
setStateなども非同期で処理するので注意!

参考記事
https://ja.reactjs.org/docs/events.html#gatsby-focus-wrapper

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

未経験がポートフォリオで使ったReactライブラリ(その3)

まえがき

業務でReactを触る機会が出てきそうなので、復習のため、以前作ったポートフォリオを個人的に振り返ります。

フロントエンド
https://github.com/momonoki1990/house_work_memo_front
バックエンド(Express)
https://github.com/momonoki1990/house_work_memo_back

サービス
https://house-work-memo-front.herokuapp.com/
(Herokuのフリープランで定期モニタリングも解除したので、起動がめちゃ遅いです(1分くらい?))
(表示が変な場合は、バックエンドの起動に時間がかかっています。そのままお待ちいただくと表示されます)

前回
未経験がポートフォリオで使ったReactライブラリ(その1)
https://qiita.com/momonoki1990/items/a1edd4fa922cd3ed3b14
未経験がポートフォリオで使ったReactライブラリ(その2)
https://qiita.com/momonoki1990/items/49f490378c724daaaf68

React Router関連

react-router-dom connected-react-router @types/react-router-dom

react-router-dom

SPAでは全てのアクセスはindex.htmlにリダイレクトされます。
その為、サーバーサイドではなくクライアントサイド(Webアプリ側)でルーティングできます。
2時間で作れる簡単フォーラムWebアプリ!
https://www.techpit.jp/courses/20/curriculums/21/sections/184/parts/663

Reactでページを切り替える(「遷移」といっていいんだろうか..)ために使います。
react-routerとreact-router-domがあり、迷いましたが、

結論
迷わずreact-router-domを使おう。
react-routerとreact-router-domの違い
https://qiita.com/koja1234/items/486f7396ed9c2568b235

とのことで、react-router-domを使いました。

connected-react-router

SPA(Single Page Application)は、描画されるコンポーネントが変わって画面が遷移したように見えてもURLは変わっていません。
なので、ユーザーはブラウザの「戻るボタン」を押しても前の画面に戻れないのですね。
ページ遷移なしで画面がヌルッと切り替わることがSPAのメリットであると同時に、ブラウザの「戻るボタン」を使えないのはユーザービリティを下げかねないですよね。
そこでconnected-react-routerを使って、SPAだけどURLルーティングを実装します。
connected-react-routerでSPAの描画をURLで切り替える
https://tech.playground.style/javascript/connected-react-router/

URLルーティングを実装するために使います。
文字だけで書いてるとわかりづらいですが、react-router-domだけだと、表示するページが変わっても、URLは変わらないし、「戻る」「進む」ボタンも使えないんですね。
connected-react-routerを使うと、react-routerによるルーティングの状態をReduxで管理できるようになります。
具体的には、表示されるページが切り替わるとURLが変わり、「戻る」「進む」ボタンが使えるようになります。

Redux Logger

redux-logger @types/redux-logger

redux-loggerは数あるredux middlewareの中で一番知られているものではないでしょうか。
(中略)
ActionがDispatchされる前後のstateとDispatchされたActionをconsole上に出力します。
意図したActionが発動しているか、その前後で期待したstateの変更が意図した通りに行われているかどうか
確認するためにはとても有用です。
redux-loggerの導入とオススメのLog出力設定の紹介
https://qiita.com/tatapopo/items/3bdf2f3132948e3d75e3

上で説明されているとおりですが、ActionをDispatchする(Reduxのstateを変更する)前後のstateの中身が見えるようになるので、便利です。
使うのも、基本的にReduxのStoreを作成する際に、applyMiddlewareに噛ませるだけなので、簡単です。

あとがき

以上です。復習のためまとめてみましたが、いろんな方の記事の切り貼りになってしまいました。
でも、それでいいのか!

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む