OmniAICreator/Qiita-1.07M huggingface dataset:
@Stateと@Bindingを使ってみた

#はじめに
SwiftUIを学ぶうちに`@State`と`@Binding`という＠がつくソースコードに出会いました!
今回はswiftでは見慣れない、この`@State`と`＠Binding`について、着目していきたいと思います。

#`@State`
###特徴
・構造体のプロパティ（変数）の値を変更できるようになります。
・`@State`がついた変数は値が変化すると、自動でViewが更新されます。

```swift:ContentView.swift
import SwiftUI

struct ContentView: View {
    @State var tapState = "ボタンをタップしてね"
    var body: some View {
        VStack{
            Text(tapState)
            Button(action:{
                //ボタンが押されたときに実行
                tapState = "タップされました！"
            }){
                Text("ボタン")
            }
        }
    }
}

struct ContentView_Previews: PreviewProvider {
    static var previews: some View {
        ContentView()
    }
}

```




<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/651213/9688ea7e-7922-8a7b-06d8-053e14f3f29d.png" width=300px>
ボタンをタップすると
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/651213/88ad1128-0c7d-c827-eb62-ce98e44e5110.png" width=300px>
となります。

これはボタンがタップされたときにtapState変数の値が書き換わり
それによりViewが更新されるためボタンの上の文字が変化します。

#`@Binding`
```swift:ContentView.swift
import SwiftUI
struct ContentView: View {
    @State var isChecked_content : Bool = false
    var body: some View {
        HStack{
            Text(isChecked_content ? "チェックされたよ": "チェックしてね！").padding(.trailing,10)
            CheckView(isChecked: $isChecked_content)
        }
    }
}

struct ContentView_Previews: PreviewProvider {
    static var previews: some View {
        ContentView()
    }
}
```

```swift:CheckView.swift
import SwiftUI

struct CheckView: View {
    @Binding var isChecked :Bool
    
    var body: some View {
        Button(action:{
            isChecked.toggle()
        }){
            Image(systemName: isChecked ? "checkmark.circle" : "circle")
                .foregroundColor(isChecked ? .blue :.gray)
                
        }
        .scaleEffect(CGSize(width: 2.0, height: 2.0))
        .frame(width: 40, height: 40, alignment: .center)
    }
}
```

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/651213/a066cb68-c69d-83a8-e78b-ef64881d2b7a.png" width=300px>
チェックマークをタップすると
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/651213/8a84458f-99de-1312-b62a-568c0b633524.png" width=300px>
となります。

チェックマークをタップすると画像がチェックマークに変わり
文言も「チェックされたよ」に変化しました。

これは`@Binging`を使用することでisChecked_contentの変数をCeckViewのisChecked変数に
バインディング（紐付けること）ができたためです。
バインディングされたことによりCheckView側で変更されたisCheckedの値が
isChecked_contentにも反映されているため文言が変化しています。

注意としてはCheckViewにisChecked_contentを渡す際に
変数の頭に$をつける状態で渡します。

また、上記コードの補足として
チェクマーク表示には[SF Symbol](https://developer.apple.com/design/human-interface-guidelines/sf-symbols/overview/)を使用しております。


#参考
[SwiftUI iPhoneアプリ開発入門ノート](https://www.amazon.co.jp/SwiftUI-iPhone%E3%82%A2%E3%83%97%E3%83%AA%E9%96%8B%E7%99%BA%E5%85%A5%E9%96%80%E3%83%8E%E3%83%BC%E3%83%88-iOS-Xcode-12%E5%AF%BE%E5%BF%9C/dp/4800712793)
unity5.2の作法 その21 minijson

#概要

unity5.2の作法、調べてみた。
minijsonやってみた。

#使用したライブラリ

https://gist.github.com/darktable/1411710


#makefile

- menu->file->new sceneする。
- menu->file->save sceneでstartとする。
- menu->gameobject->create emptyする。
- menu->assetes->creates->c# scriptでstart.csつくる。
- ダブルクリックして、コードを書く。
- ヒエラルキーのgameobjectに、コードを重ねる。
- 三角で実行。


#サンプルコード

```
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
using System.IO;
using System;
using System.Text;
using MiniJSON;

public class mini : MonoBehaviour {
    public string jsonFileName;
    Dictionary<string, object> response;
    void Update() {
        if (Input.GetKeyDown(KeyCode.Space))
        {
            ReadFile();
        }
    }
    void OnGUI() {
        if (response != null)
        {
            GUI.color = Color.yellow;
            GUI.TextArea(new Rect(0, 0, Screen.width, Screen.height), "name:" + response["name"]);
        }
    }
    void ReadFile() {
        string fileText = "";
        Debug.Log(Application.dataPath + "/" + jsonFileName);
        FileInfo fi = new FileInfo(Application.dataPath + "/" + jsonFileName);
        using (StreamReader sr = new StreamReader(fi.OpenRead(), Encoding.UTF8))
        {
            fileText = sr.ReadToEnd();
            Debug.Log(fileText);
            response = Json.Deserialize(fileText) as Dictionary<string, object>;
            Debug.Log(response["name"]);
        }
    }
}


```

以上。
引数と中身の処理内容の不一致

![スクリーンショット 2021-07-03 10.28.42.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1286751/0a167b80-d6ad-8950-2d13-e36bb5bd341d.png)



<修正前>


```form_presenter.rb

def date_field_block(name, label_field , options = {})
    markup(:div ,class: "input-block") do |m|
    m << decorated_label(name , label_text  , options )
    m << date_field(name ,options)
    m << error_messages_for(name)
    end
  end
```





<修正後>


```form_presenter.rb

def date_field_block(name, label_text , options = {})　　　　　　#<=ここを修正
    markup(:div ,class: "input-block") do |m|
    m << decorated_label(name , label_text  , options )
    m << date_field(name ,options)    
    m << error_messages_for(name)
    end
  end
```

引数と処理の内容が一致していませんでした。
Next.js + TypeScript 外部パッケージの型対応手順

![title.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/166484/a6d49aee-c546-3a1e-8c45-a830ad2ed731.png)


Next.jsプロジェクトにTypescriptを導入すること自体は、Next.jsの[公式チュートリアル](https://nextjs.org/learn/excel/typescript)に従って行えば簡単に行なえます。
ですが、実際の開発ではFirebaseのような外部パッケージを追加するため、それら外部パッケージに対しても当然 型対応を行う必要があります。

この記事は、これら外部パッケージについて、どういった手順で型対応を行うのか、また型定義の見つけ方についてまとめました。

外部パッケージの型対応は、以下の３つステップを踏んで行います。

- 厳密な型定義チェックを有効にする
- 外部パッケージの型定義を用意する
- コードの修正

## 手順

### Step1. 厳密な型チェックを有効にする

Next.jsは、TypeScriptを導入直後のデフォルトの状態では、厳密な型チェックは行われません。
まず、`tsconfig.json`ファイルの`strict`オプションを有効にし、厳密な型チェックが行われるよう設定を修正します。

```json:tsconfig.json
{
  "compilerOptions": {
    "strict": true, // trueに修正
    // ...
  }
}
```

### Step2. 外部パッケージの型定義の用意

型定義を用意する方法は３つあります。
それぞれの方法について説明します。

#### 方法１. 外部パッケージに型定義が含まれている場合

あらかじめ外部パッケージに型定義がパッキングされているケースです。
この場合は、そのまま型定義を利用することができます。
パッケージ内に型定義があるかの確認は、以下で判断が可能です。

- `node_modules`のパッケージ内の`package.json`に`types`フィールドに型定義への参照を持っているか？
- `node_modules`のパッケージ内に`パッケージ名.d.ts`ファイルが作成されているか？
- [npmパッケージの詳細ページ](www.npmjs.com)に`TS`のマークが付いているか？

![mark.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/166484/da81f96f-1bed-6f80-dc9e-38f6e52809c3.jpeg)

上図からfirebaseのパッケージは、`TS`マークが付いているのでパッケージに型定義が同梱されていることがわかります。

#### 方法2. パッケージと別の型定義ファイルを探す

もし方法１で型定義が見つからなければ、パッケージ名の接頭に`@types/パッケージ名`となっているnpmパッケージを検索します。
以下の方法で型定義が無いか探してみます。

- 外部パッケージの`README`に`@types/パッケージ名`が無いか確認。
- 型定義の検索サイト[TypeScript Types Search](https://www.typescriptlang.org/dt/search?)で検索します。

![sc.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/166484/83ac92bf-c5fa-5d9c-707c-e57ff2e47d35.png)

#### 方法3. 型定義を自作する

もし既存の型定義が見つからない場合、型定義を自作します。
`src/types/`フォルダ下に、ファイル拡張子`.ts`などとし定義ファイルを作成します。

```json:tsconfig.json
"include": {
  "types/**/*"
}
```

```typescript:types/sample.ts
export type PersonType = {
  id: string;
  name: string;
  age: number;
};
```

### Step3. コードの修正

外部パッケージの型定義の準備できたら、コードの修正にかかります。

エディッタに[VSCode](https://code.visualstudio.com/)を使用している場合、修正箇所を闇雲に探す必要はありません。
コード中の型定義されていない箇所に自動で赤マーカーが表示されます。
これら赤マーカーの箇所を順番に修正していくことで、自然に外部パッケージの型対応は完成します。

## おわりに

Next.jsの外部パッケージの型対応の手順の説明は以上となります。
最後まで読んで頂きありがとうございました。

## 参考

- https://nextjs.org/learn/excel/typescript
- https://github.com/microsoft/TypeSearch
- WEB/DB Press vol.117 TypeScript
unity5.2の作法 その20 simplejson

#概要

unity5.2の作法、調べてみた。
simplejsonやってみた。

#使用したライブラリ

http://wiki.unity3d.com/index.php/SimpleJSON


#makefile

- menu->file->new sceneする。
- menu->file->save sceneでstartとする。
- menu->gameobject->create emptyする。
- menu->assetes->creates->c# scriptでstart.csつくる。
- ダブルクリックして、コードを書く。
- ヒエラルキーのgameobjectに、コードを重ねる。
- 三角で実行。


#サンプルコード

```
using UnityEngine;
using System.Collections;
using System.IO; 
using System; 
using System.Text;
using SimpleJSON;

public class sample : MonoBehaviour {
    public string jsonFileName;
    private JSONNode json;
    void Update () {
        if (Input.GetKeyDown (KeyCode.Space)) 
        {
            Debug.Log("ok");
            ReadFile ();
        }   
    }
    void OnGUI() {
        if (json != null) 
        {
            GUI.color = Color.yellow;
            GUI.TextArea (new Rect (0, 0, Screen.width, Screen.height), "name:" + json["name"]);
        }
    }
    void ReadFile() {
        string fileText = "";
        Debug.Log(Application.dataPath + "/" + jsonFileName);
        FileInfo fi = new FileInfo(Application.dataPath + "/" + jsonFileName);
        {
            using (StreamReader sr = new StreamReader(fi.OpenRead(), Encoding.UTF8))
            {
                fileText = sr.ReadToEnd();
                Debug.Log(fileText);
                json = JSONNode.Parse(fileText);
            }
        }
    }
}




```

以上。
コミットメッセージの変更をする

#はじめに
コミットメッセージの履歴の一覧を目にすると些細な表現の違いが気になってしまった。変更方法がわからなかったので改めてコミットメッセージの操作について触れてみる。

#直前のコミットメッセージを変更する
```terminal
#直前のコミットメッセージの変更
git commit --amend

#ワンラインでのメッセージの変更
git commit --amend -m "変更メッセージ"
```
これは直前のコミットまでを修正するコマンド。

#過去に遡りコミットメッセージを変更する
`git log --oneline`とコマンドを叩いて、下記のようなコミット履歴があるとする。

```terminal
#ハッシュID   コミットメッセージ
f234304 (HEAD -> master, origin/master, origin/HEAD) pre-commitの追加
1fb1c3b Rubocopの追加
1328f68 RSpecの実装
fc36a2b platform を追加
ce96219 init
```
上が最新のコミット履歴。
左の`f234304`がコミットのハッシュID。
右の`HEAD`は現在いるブランチ。
`XXの追加`とされているのがコミットメッセージ。

今回は`RSpecの実装`を追加に変更したい。

```terminal
#HEADから指定の位置までを指定
git rebase -i HEAD~3

#ハッシュIDで位置を指定
git rebase -i 1328f68
```
`HEAD~3`とは最新のコミット履歴の上から３番目まで、という意味。
`1328f68`はそのまま、その位置を指定している。

vimエディッタが開くので下記の手順で記述を修正する。

```vim
#変更前
pick 53fac6e RSpecの実装
pick f997d47 Rubocopの追加
pick 8e43d8f pre-commitの追加

#変更後
edit 53fac6e RSpecの実装
pick f997d47 Rubocopの追加
pick 8e43d8f pre-commitの追加
```
①`i`キーを押してインサートモードに切り替え
②変更したいコミットメッセージの`pick`を`edit`に変更
③`Esc`キーを押してコマンドモードに切り替え
④`:wp`キーで保存して終了

```terminal
#変更したいメッセージを入力。
git commit --amend -m "RSpecの追加"
```
最後に最初で説明したコマンドを叩いて完了。

```terminal
8e43d8f (HEAD -> master) pre-commitの追加
f997d47 Rubocopの追加
53fac6e RSpecの追加
fc36a2b platform を追加
ce96219 init
```
`git log --oneline`で確認して変わっていればOK。
最後に`git rebase --continue`を叩いて編集を終了させて完了。

#GitHubのコミットメッセージの変更
上記の変更を行った場合、ローカルとリモートで履歴に違いが出てしまっているので`push`できない。

```
#push時のエラー
To https://github.com/XXXXXX/sample_app.git
 ! [rejected]        HEAD -> master (non-fast-forward)
error: failed to push some refs to 'https://github.com/XXXXXX/sample_app.git'
hint: Updates were rejected because the tip of your current branch is behind
hint: its remote counterpart. Integrate the remote changes (e.g.
hint: 'git pull ...') before pushing again.
hint: See the 'Note about fast-forwards' in 'git push --help' for details.
```

`git push origin HEAD`が拒否されてしまうので、`-f`オプションをつけて強制実行。

`git push -f origin HEAD`

これでGitHub上のコミットメッセージも変更されているはず。
今回のケースは個人のリポジトリを変更しているので気にせず`-f`オプションをつけてみたが、共同開発していた場合などはちょっと怖いやり方らしいので注意。

#参考元
[Gitのコミットメッセージを後から変更する方法をわかりやすく書いてみた](https://www.granfairs.com/blog/staff/git-commit-fix)
[過去にリモートへpushしたコミットのコメントを変更してみる
](https://saikeblog.com/2019/04/20/%E9%81%8E%E5%8E%BB%E3%81%AB%E3%83%AA%E3%83%A2%E3%83%BC%E3%83%88%E3%81%B8push%E3%81%97%E3%81%9F%E3%82%B3%E3%83%9F%E3%83%83%E3%83%88%E3%81%AE%E3%82%B3%E3%83%A1%E3%83%B3%E3%83%88%E3%82%92%E5%A4%89/)
WordPressのGutenbergで画像リンク先基本設定をメディアファイルに

画像ポップアップ表示のプラグインは、メディアリンク設定がないと機能しなかったので。。

基本設定でリンク有りにしたかったのでメモ

設定する前のImageブロックでは設定が反映されなかった感じがします

新しくブロックを追加後に動作確認できたと感じます

![スクリーンショット 2021-07-03 10.01.43.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/48015/f2de1aa5-e4c7-3b72-073a-f9b364627bf5.png)


### 設定方法１

``` funciton.php
add_action('after_setup_theme', function () {
  update_option('image_default_link_type', 'file');
});
```

###設定方法２

wp-admin/options.phpのページで「image_default_link_type」を「file」に設定

![スクリーンショット 2021-07-03 10.15.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/48015/b1dd41fb-ae75-bf51-60ed-5d6a2a324867.png)




### 参考サイト

https://github.com/WordPress/gutenberg/pull/25578

https://www.imaginationdesign.jp/blog/wordpress/3618/
cscの作法 その48 json

#概要

cscの作法、調べてみた。
jsonやってみた。

#使用したライブラリ

http://wiki.unity3d.com/index.php?title=UnityLitJSON

#サンプルコード

```
using System.Collections;
using System.IO;
using System;
using System.Text;
using LitJson;

namespace Test {
	class test0 {
		static void Main() {
			Console.WriteLine("hello world!");
			string jsonFileName = "sample.json";
			string fileText = "";
			FileInfo fi = new FileInfo(jsonFileName);
			using (StreamReader sr = new StreamReader(fi.OpenRead(), Encoding.UTF8)) {
				fileText = sr.ReadToEnd();
				Console.WriteLine(fileText);
				LitJson.JsonData json = LitJson.JsonMapper.ToObject(fileText);
				Console.WriteLine(json["name"]);
			}
		}
	}
}



```

以上。
Quest 2 を Oculus Link で繋いでるのに、Unity の Play Mode に入っても、HMD 側でなにも起こらないんだけど？

というときは、XR Plug-in Management で、PC のタブでも Oculus にチェックが入ってるか確認してください。
![20210703-085756.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/253921/e8d75c5f-d07b-f0a5-799d-daa1169c62c6.png)
Djangoであいまい検索をする

Djangoに元々備えられているfilter()メソッドを使用する際に、通常は
　　モデル.objects.all().filter(○○ = ●●）
としますが、
　　モデル.objects.all().filter(○○＿_contains = ●●)
と記載すると、項目○○に対して●●を含むデータを取得できます。また、
　　モデル.objects.all().filter(○○＿_startswith = ●● )
で、項目○○に対して先頭が●●で始まるデータが取得ができます。更には、
　モデル.objects.all().filter(○○＿_endswith = ●● )
で、最後が●●で終わるデータの取得もできます。
その他、大文字小文字の区別をしない検索や比較演算を行う検索方法などもあり、
また、検索したいワードが複数ある場合、複数ある検索ワード●●を●●●●へリスト化して
　モデル.objects.all().filter(○○＿_in) = ●●●●
とすることで、検索ができます。
Amazon Cognito 外部IDプロバイダ連携 メモ

* Amazon Cognitoと外部IDプロバイダとの連携方法についてメモする。

## Amazon Cognitoとは

* ウェブおよびモバイルアプリの認証、承認、およびユーザー管理機能を提供するAWSサービス。

* API ベースで実装されるモバイルアプリやWeb アプリに機能を提供する。
* ユーザープール
  * アプリユーザーのサインアップとサインインオプションを提供するユーザーディレクトリ機能

* IDプール
  * AWS の他のサービスに対するアクセスをユーザーに許可する機能

### 外部IDプロバイダとの連携

![cognito_idp.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/586535/a8e2d292-9409-e5f7-b2df-915bef4dd1a7.png)


* 外部IDプロバイダ(ID管理機能を提供するサービス)とIDフェデレートすることができる。
* Cognitoが連携できるIDプロバイダ
  * ソーシャルIDプロバイダ
        * Facebook
        * google
        * Login With Amazon
        * Sign in With Apple　など
  * SAMLプロバイダ：[SAML 2.0 標準](http://saml.xml.org/saml-specifications)をサポートするプロバイダ
        * [Microsoft Active Directory フェデレーションサービス (ADFS)](https://msdn.microsoft.com/en-us/library/bb897402.aspx) 
        * [Shibboleth](http://www.shibboleth.net/) など
  * Open ID Connect： [OpenID Connect (OIDC)](http://openid.net/specs/openid-connect-core-1_0.html) ID プロバイダ
        * [Salesforce](https://developer.salesforce.com/page/Inside_OpenID_Connect_on_Force.com)
        * [Ping Identity](https://www.pingidentity.com/developer/en/index.html)など



## 連携準備

1. 事前準備 : 次のものを用意する。
   1. アプリケーションクライアントとユーザープールドメインが作成されたユーザープール※[ユーザープールの作成](https://docs.aws.amazon.com/cognito/latest/developerguide/cognito-user-pool-as-user-directory.html)
   2. ソーシャル ID プロバイダー。

2. IDプロバイダに登録する。
   * 連携するIDプロバイダでクライアントID/シークレットの発行、リダイレクトURIの登録などを行う。

3. [ユーザープールに OIDC IdP を追加する](https://docs.aws.amazon.com/ja_jp/cognito/latest/developerguide/cognito-user-pools-oidc-idp.html#cognito-user-pools-oidc-idp-step-2)。
   *  IdP からの OIDC ベースの認証リクエストを処理するようにユーザープールを設定する。

     

   

## 連携概シーケンス

![cognito_idp_sequence.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/586535/5bddac46-bc8c-01f6-a839-15d3755db8c2.png)



## 参考情報

* [Amazon Cognito とは](https://docs.aws.amazon.com/ja_jp/cognito/latest/developerguide/what-is-amazon-cognito.html)
* [Amazon Cognito ユーザープール Auth API リファレンス](https://docs.aws.amazon.com/ja_jp/cognito/latest/developerguide/cognito-userpools-server-contract-reference.html)
【GAS】値一覧をフィルタ材料にして、スプレッドシートを絞り込み表示させるスニペット


## 概要

登録した何とかID一覧をスプレッドシートから取り除きたいという場合に使える小技。

## 手順

まず、`main`タブにフィルタさせたいスプレッドシートを用意。

また、A列がフィルタの材料となる列にする。

![スクリーンショット 2021-07-03 9.37.49.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/494166/fa5b7bec-f935-9c60-8fd2-97dcc08883d8.png)


次に`hiddenValueList`タブを用意。A列に非表示にしたい値を並べる。

![スクリーンショット 2021-07-03 9.38.01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/494166/9f637455-a307-acaa-f1d4-3e4bfb8701a4.png)

そしてGoogle Apps Scriptから次のスニペットを実行

※ Sheets APIを利用するので事前にサービスを追加しておく。

```javascript

function myFunction() {
  const spreadsheet = SpreadsheetApp.getActiveSpreadsheet();
  const hiddenValueList = spreadsheet.getSheetByName('hiddenValueList');
  const hiddenIds = hiddenValueList.getRange(1, 1, hiddenValueList.getLastRow()).getValues().flat();
  const main = spreadsheet.getSheetByName('main');

  var filterSet,columnIndex,request

  filterSet = {};

  filterSet.range = {
    sheetId:main.getSheetId()
  }; 

  filterSet.criteria = {};

  columnIndex = 0;

  filterSet['criteria'][columnIndex]={
    'hiddenValues':hiddenIds
  };

  request = {
    "setBasicFilter": {
      "filter": filterSet
    }
  };

  Sheets.Spreadsheets.batchUpdate({'requests': [request]}, spreadsheet.getId());
}


```

実行結果は下記。

`みそ`と`とんこつ`が非表示になっている。

![スクリーンショット 2021-07-03 9.38.19.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/494166/21e94518-e926-6776-be7f-381444e51a98.png)


## 参考

Google apps script でfilterをかける方法｜Sheet APIと連携したら上手くいった

https://xn--t8j3bz04sl3w.xyz/google-apps-script/filter/3874/2/
before_actionを使って同じコードをメソッドにまとめよう！

コードを記述する際、同じ記述を繰り返ししないといけない時があると思うが
そんな時はbefore_actionとonlyオプションを駆使して可読性を高めよう！

```ruby
class ItemsController < ApplicationController
  before_action :authenticate_user!, except: [:index, :show]
  before_action :set_item, only: [:show, :edit, :update, :destroy]

  def index
    @items = Item.all.order('created_at DESC')
  end

  def new
    @item = Item.new
  end

  def create
    @item = Item.new(item_params)
    if @item.save
      redirect_to root_path
    else
      render :new
    end
  end

  def show
  end

  def edit
    unless @item.user == current_user
      redirect_to root_path
    end
  end

  def update
    unless @item.user == current_user
      redirect_to root_path
    end
    if @item.update(item_params)
      redirect_to item_path(@item.id)
    else
      render :edit
    end
  end

  def destroy
    unless @item.user == current_user
      redirect_to root_path
    end
    @item.destroy
    redirect_to root_path
  end


  def item_params
    params.require(:item).permit(:image, :product_name, :product_descriiption, :category_id, :product_condition_id, :price,
                                 :shipping_charge_id, :delivery_area_id, :days_to_delivery_id).merge(user_id: current_user.id)
  end

  private

  def set_item
    @item = Item.find(params[:id])
  end
end
```
先ず３行目の

```ruby
before_action :set_item, only: [:show, :edit, :update, :destroy]
```

before_actionを使い処理させたいメソッドを記述。
こちらの場合は:set_itemが処理させたいメソッドに該当する。
次にonlyオプションを使いどのアクションの実行前に処理を実行するのか記述。
ここではshowアクション、editアクション、
updateアクション、destroyアクションで同じ記述を実行させたいということ。

ではその処理させたいメソッドの内容はどこに記述しているのかというと
５７行目以降の

```ruby
 private

  def set_item
    @item = Item.find(params[:id])
  end
```

こちらの記述で呼び出している。
レーザー彫刻機２号機　部品調達　その2

# 部品調達　その2

##アクリル外装
煙で部屋がくさくなるので、アクリルの外装があると助かります。

1品ものやサイズの大きなものは、
カットサービスがある国内のアクリル販売店に注文しました。

アクリルショップはざいや
https://www.hazaiya.co.jp/

オンラインで数値入力による自動見積＆注文ができる安くて非常に便利なありがたい業者さん。
ほぼどんな形にでも対応できるオンライン見積ツールです。
直角平行と円しかない部品であれば、入力に少し手間はかかりますが、他のイラストレーターファイル入稿での業者さんよりも大幅に安くて早いです。
バックパネル
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/664748/b9113e98-d163-6675-9394-e46f05f6877a.png)
サイドパネル
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/664748/584b885e-906b-68c3-765e-6c910400e599.png)
その他
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/664748/8fe2d97d-3d82-721f-cadc-a7454884642f.png)

##アクリル部品
モーターベースやガイドの接続プレートなどの小さい部品は、elecrowを使ってみました。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/664748/3a8bb515-b772-59cd-d9a6-8c79d8e9f977.png)

https://www.elecrow.com/acrylic-cutting.html

選んだサイズのアクリル板に入れば、どんな形でも何個でも5枚カットしてくれるので
サイズが同じ形が複数枚必要な場合などはとてもお得です。
dxfファイルをアップロードして注文。

精度に関しては、上記の業者さんよりも少し悪いです。
特に穴の精度が良くなかったです。いくつかボルトが通らなくてヤスリで削りました。
12間表示（AM:PMつき）の時刻の差を求める

最後は、別の人が答えた....
ヒントを与えたので後は自力でと思ったんですが、結局できなかったようですね。
これでは、いつまでたっても自分ではできんだろうなぁと思う。まぁいいか私じゃないし、人それぞれ。

しかし、この質問は結構ハードだったけど、また、回答しても理解してもらえない。


```
(((
IF(LEFT(TEXT(End_Time__c),2)="12", 0, VALUE(LEFT(TEXT( End_Time__c ),FIND(":", TEXT(End_Time__c ))-1)))+
IF(CONTAINS( TEXT(End_Time__c),"PM" ),12,0))
*60+VALUE(MID(TEXT(End_Time__c ),FIND(":", TEXT(End_Time__c ))+1,2)))
-
((
IF(LEFT(TEXT(Start_Time__c ),2)="12",0, VALUE(LEFT(TEXT( Start_Time__c  ),FIND(":", TEXT(Start_Time__c  ))-1)))+

IF(CONTAINS( TEXT(Start_Time__c ),"PM" ),12,0))


*60+VALUE(MID(TEXT(Start_Time__c  ),FIND(":", TEXT(Start_Time__c  ))+1,2))))/60
```

https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000BdJm9
Github Actionsでgradleコマンドの実行がPermission deniedになる

# この記事は？
GitHubActionsでgradleを使用してビルドを行ったときにPermission deniedとなってしまいました。
本記事ではその時にどのように解決したかについて紹介します。

# 対応方法
gradleコマンドの実行の前に下記の通りgradlewに実行権限を付与してあげることで実行することができるようになります。

``` yaml
      - name: Make gradlew executable
        run: chmod +x ./gradlew
```

# ちなみに
最初これで解決しようとしました。


``` yaml
      - name: Build
        run: sudo ./gradlew build
```

この場合は以下のようにエラーがでてしまうので対応できませんでした。
`sudo: ./erp/gradlew: command not found`

原因を深く追求はしていませんが、この対応方法ではだめなのようです

# おわりに
Github Actionsを使っている記事がそもそも少なく、案外始めるにも大変だなと思いましたが、はまりどころを解消すれば簡単にCIできて良いなと思いました。
【Rails】超便利なScaffoldの使い方を紹介

####My Profile
プログラミング学習歴②ヶ月目のアカウントです！
プログラミングスクールで学んだ内容や自分が躓いた箇所等のアウトプットの為に発信しています。
また、プログラミング初学者の方にわかりやすく、簡潔にまとめて情報共有できればと考えています。
もし、投稿した記事の中に誤り等ございましたら、コメント欄でご教授いただけると幸いです。　


#対象者

・簡単にrailsのモデル、コントローラー、ビュー、ルーティングを作りたい方

・数分で簡単なプログラミングを作りたい方

#手順目次
1.rails newでアプリケーションを新規作成

2.scaffoldで一括作成

3.注意点


#実際の手順と実例
###1.rails newでアプリケーションを新規作成
今回はexampleアプリケーションを作成しました。

`````
rails new example
```

###2.scaffoldで一括作成

ここで下記のコマンドをターミナルに打ち込んで行きます

````
rails generate scaffold モデル名 カラム名1:データ型1,,,,,,,,
````

ここではUserモデルを作成してみます！
実例を上げると、下記の通りです。

````
rails generate scaffold user name:string emai:integer
````

カラムはUserの情報に必要なnameとemaiを選択しました。
stringは短い文章を入力するためのカラムのデータ型です。

実行後はデータベースにデータモデルを反映させるために
**rails db:migrate**を忘れず実行しましょう。

こちら実行後はUserモデル、Usersコントローラー、
各ビューページ、ルーティングまで一括作成されます。
とても便利なのでぜひ活用してみてください！

###3.注意点

以下はRails tutolialから引用した注意点です。
下記の項目に注意しながら使いましょう


>2.2.3 Usersリソースの欠点　Rails tutolial
>
scaffoldで作成したUsersリソースは、Railsの概要を手っ取り早く説明するには良いのですが、次のようなさまざまな問題点を抱えています。
>
①データの検証が行われていない。 
　このままでは、ユーザー名が空欄であったり、でたらめなメールアドレスを入力したりしても通ってしまいます。
②ユーザー認証が行われていない。
　 ログイン、ログアウトが行われていないので、誰でも無制限に操作できてしまいます。
③テストが書かれていない。 
　厳密にはこれは正しい表現ではありません。というのも、scaffoldで生成したコードにはごく簡単なテストが一応含まれているからです。ただ、scaffoldのテストコードはデータ検証やユーザー認証、その他の必要な要求を満たしていません。
④レイアウトやスタイルが整っていない。
 サイトデザインも操作法も一貫していません。
⑤理解が困難。 scaffoldのコードを理解できるぐらいなら、そもそも本書を読む必要はないでしょう。

また、⑤に関連しますが、MVCモデルでどのような流れでブラウザにサイトが表示されるかを把握しておく必要があるかと思いますので注意して使いましょう！
Macアドレス有りEEPROM

# EEPROM内のMacアドレスをRead

秋月電子で販売されている[Macアドレス書き込み済みEEPROM](https://akizukidenshi.com/catalog/g/gI-01412/)からMacアドレスを読んでみる。

## 環境
Arduino IDEおよびArduino Unoを利用。

## ATMEL AT93C46A/AT93C46D
EEPROM自体はATMEL AT93C46A/AT93C46D。

### AT93C46A/AT93C46Dデータシート
秋月電子の本製品の[ページ](https://akizukidenshi.com/catalog/g/gI-01412/)からたどれる。SPI接続でEEPROM領域へアクセス可能。

### 参照ソースコード
このEEPROMへのアクセスするソースコードサンプルは[ここ](https://github.com/0xJoey/Arduino_93C46)に見つかる。これをほぼそのまま使う。

### ソースコード
下記10-13は、ArduinoでSPI接続する場合のピン番号である。

```c++
#include "93C46.h"

#define pCS 10
#define pSK 13
#define pDI 11
#define pDO 12

// Prints all words of the buffer
void debugPrint(word* buff, int len) {
  char buf[4];
  
  Serial.print("\n   00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F");
  for(int i = 0; i < len; i++) {
    if(i % 8 == 0) {
      Serial.println();
      sprintf(buf, "%02x", i*2); Serial.print(buf);　Serial.print(" ");
    }
    sprintf(buf, "%02x", buff[i] & 0xFF); Serial.print(buf);
    Serial.print(" ");
    sprintf(buf, "%02x", (buff[i] & 0xFF00) >> 8); Serial.print(buf);
    Serial.print(" ");
  }
  Serial.println();
}

void setup() {
  bool longMode = EEPROM_93C46_MODE_16BIT;
  
  eeprom_93C46 e = eeprom_93C46(pCS, pSK, pDI, pDO);
  e.set_mode(longMode);
  Serial.begin(9600);
  
  int len = longMode ? 64 : 128;
  word readBuffer[len];
  for(int i = 0; i < len; i++) {
    // Read by address
    word r = e.read(i);
    readBuffer[i] = r;
  }
  debugPrint(readBuffer, len);
  Serial.println();
}

void loop() {}
```

## 結果
上記コードの実行結果は下記のとおり。

```
   00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F
00 40 00 10 00 00 02 cb XX XX XX 00 00 00 00 00 00 
10 00 00 ff ff ff ff ff ff ff ff ff ff ff ff ff ff 
20 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff 
30 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff 
40 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff 
50 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff 
60 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff 
70 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
```

本EEPROMに関する秋月電子の[Ｑ＆Ａページ](https://akizukidenshi.com/catalog/faq/goodsfaq.aspx?goods=I-01412)によると、販売メーカーが取得したベンダーコード「00 02 cb」が見える。その次に続く「XX XX XX」が連番のデータ。

## 最後に
上述のリンク先のソースコードを利用すれば、EEPROMのMacアドレス領域に書き込めるはず。ただし、Macアドレスのユニーク性が保証されなくなるので注意されたし。
ラムダ式を使ってリスト配列からローマ字を大文字から小文字に変換するプログラム

ラムダ式を使ってリスト配列からローマ字を大文字から小文字に変換するプログラムを作りました。

```Java

// 乃木坂新4期生メンバーをローマ字の大文字から小文字に変換する
// Create  2021/7/3
// Author  乃木坂好きのITエンジニア
//
//
//

//APIのimport
import java.util.ArrayList;
import java.util.Scanner;


class NewYonki {
	public static void main(String[] args) {
		ArrayList<String> name_list = new ArrayList<String>();
		Scanner sc = new Scanner(System.in);
		System.out.println("人数を5人ローマ字大文字で入力してください");
		for(int i=0;i<5;i++) {
			String line = sc.nextLine();
			name_list.add(line);
		}
		//ラムダ関数でリスト配列の要素を全て小文字にする
		name_list.replaceAll(s -> s.toLowerCase());
		System.out.println(name_list);
　　　　sc.close();

	}
}
```

ラムダ関数を使うとプログラム作成が楽ですね
ASLRの有効bit数

32bitOSにおいてASLRは16bit分しか提供しない といった旨の記述がReturn-to-libc攻撃のwikipediaに書いてあり、理由が気になったので雑にメモ。
2通りで調べたのでそれぞれ書きます。

1. まず、英語版の出典はスタンフォードの論文pdfでした。
この3.3.2によれば、32bitのうち12bitはオフセットに(後述)、残り20bitのうち、4bitは仮想メモリ空間のフラグメンテーションを防ぐためにランダム化できないため、残りの16bit分のみASLRが提供される とのこと。 (これは最大16ということで、実際は12bitなども見られるようで....)
64bitOS上の32bit互換で実行する場合も同様に脆弱であると述べてあります。
64bitOSにおいては最低でも40bitがランダム化されるとのことです。

2. また、32bitOS(x86)のメモリ管理の観点から、まずセグメント方式について知る必要がありそうだと考えました。 結果として間違いではありませんでしたが....
元々、ASLRは12bitに働いていたという検証も見ており、セグメントのリアルモードのオフセット12bitをランダム化しているのかな などと思っていたのですが全く的を射ない思考でした。
実際は上記の通り、残りの20bitの中から一部ランダム化されているようです。




32bitの半分だから16bit という訳ではなくメモリ管理との兼ね合いがあるようですね。
ソース: https://web.stanford.edu/~blp/papers/asrandom.pdf
Djangoでフォームから入力された値を取得する方法

Djangoでフォームへ入力された値を取得する方法。
・request.POSTを引数にしてインスタンス化したフォーム（formとします）にis_valid()メソッドを実行。is_valid()はフォームから入力された値が有効かどうかをDjango側が調べてくれるメソッドです。通常は「フォームの値が有効ならば次の処理を行う」という形でif文と一緒に使用されます。
　　form = フォーム名(request.POST)
　　if form.is_valid():
すると、
　　form.cleaned_data['項目名']
で値を取得することができるようになります。
・もう一つは、is_valid()が不要な場合、単に
　　request.POST['項目名']
でも取得可能です。
何度か画面遷移をして複数のviewが実行される中で、違うviewで一度is_valid()を行ったformに対して、値を取得したいがために再びis_valid()を実行していたことがあったので、そのような場合は単にrequest.POSTで済みます。
amplify CLI の Headless mode で pull するとき auth リソースが存在するとエラーで落ちる

# 前提
- Amplify CLI バージョン 4.52.0

# 問題
AWS Amplify を使ったアプリを CI で自動ビルドするときなどは `amplify pull` を Headless mode で使って、設定を自動化します。公式ドキュメントの [Headless mode の説明](https://docs.amplify.aws/cli/usage/headless#amplify-pull-parameters)に従って、スクリプトを書くと次のような感じになります。

```bash
#!/bin/bash

AMPLIFY="..." # 略
FRONTEND="..." # 略
PROVIDERS="..." # 略

amplify pull --amplify $AMPLIFY --frontend $FRONTEND --providers $PROVIDERS --yes
```

しかし、 pull 対象の Amplify に auth リソース （Cognito) が設定されていると、以下のようなエラーが出る場合があります。

```bash
Failed to pull the backend.
auth headless is missing the following inputParams userPoolId, webClientId, nativeClientId
```

# 原因
`amplify pull` に `--yes` オプションを付けていると、 pull 後に auth リソースの初期化が実行されることが原因です。試しに　`--yes` オプションを付けないとどういう動作になるかというと、

```sh
% amplify pull --amplify $AMPLIFY --frontend $FRONTEND --providers $PROVIDERS
Amplify AppID found: <your_app_id>. Amplify App name is: my_app
Backend environment dev found in Amplify Console app: my_app
? Do you plan on modifying this backend? (Y/n)
```

最後に「バックエンドを更新する予定があるか？」という質問が出ていることが分かります。

この質問に手動で `Y` と回答した場合は、 そのまま処理が成功するのですが、不思議なことに `--yes` オプションを使った場合は、 その後、auth リソースの初期化が走り、さらに初期化に必要な設定が見つからずに、エラーになるようです（そもそも初期化が走るのはバグのような気もしますが...）。

# 対策
「バックエンドを更新する予定はない」という設定で `amplify pull` を実行させるのが対策になります。

しかし、2021年7月現在、`amplify pull` の Headless mode には、バックエンドを更新する予定の有無を設定するオプションは存在しません。また、「バックエンドを更新するか？」という質問に `no` で回答するオプションもありません。

ということで、強引にパイプで `n` を突っ込む、次のワークアラウンドが対策となります。

```sh
echo n | amplify pull --amplify $AMPLIFY --frontend $FRONTEND --providers $PROVIDERS
```

# 参考
- [Headless amplify pull without modifying the backend](https://github.com/aws-amplify/amplify-cli/issues/5275)
Mackerelでグラフ共有をやってみる

# はじめに
https://mackerel.io/ja/docs/entry/howto/view-graphs
より、グラフ共有機能を試してみる
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/416263/f8a3992a-ef2d-2738-399c-c37cd469b476.png)

# グラフ共有をやる
自前のdiskグラフを題材にどんなもんか見てみる。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/416263/a968698e-f8de-9758-249a-8129dfd4d03d.png)

## グラフダウンロードの場合
png形式のファイルがローカルPCへDLできた。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/416263/3d5e823a-f3d9-220d-bd85-cbc3f3ea95d8.png)

実際の画像はコチラ。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/416263/e4ae9e9a-37d0-bded-cebb-d27ad7a2b5e5.png)


## "リンク"のURLの場合
結果がコチラ。直近６Hとか直近１日とかグラフが抜き出せて操作もできる。
自分がやりたかった共有のイメージに一番近い感じ。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/416263/2731b2cc-9fee-bb2f-f70c-1f5ff8515313.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/416263/702bf06b-1875-1eba-d832-af3fb7674f8e.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/416263/1b3cf0d7-34e2-0127-6aff-f9f2e16812f0.png)


## 埋め込みの場合
iframe, 画像, SVG, MarkDownと選べるようなのでそれぞれの結果を比較。
iframeは凡例が見える分、良心的。他は…少し前に試したLINE通知で受け取った画像と似たようなクオリティ。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/416263/9973ee8c-d8a8-c9dd-ace0-e253648349b2.png)

MarkDown形式のは↓↓の画像。、、、Qiitaだったら埋め込めるかなって思ったけど
うまく認証が聞いてない感じ。「できそう」感はあったので惜しかった。結果、どうやったら見れるのかよくわからなかった。
※後で”公開URL”版であれば見れることがわかったのでここは見れないってことで問題なし
[![graph](https://mackerel.io/embed/orgs/watyanabe164/hosts/4gzbfytYgKW.png?graph=disk&amp;period=1h)](https://mackerel.io/orgs/watyanabe164/hosts/4gzbfytYgKW/-/graphs/disk#period=1h)


![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/416263/29910cdd-8a06-d146-0b7f-d974243f7502.png)

## グラフを公開、の場合
さらにiframe, 画像、SVG、MarkDownが選べる公開URL版のものが出てきた。
どうやら「埋め込み」のURL使って表示できるのはオーガニゼーションへログインできる人だけ見れるものなのかもしれない、と思った。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/416263/0b8d757a-4e2b-1d19-e136-495caa1e249b.png)

↑↑の「リンク」で表示できなかった、Markdown形式をここで試すと、思った通り表示できた。
ブログとかにマカレルのグラフをMarkDownで表示させたいときは公開ＵＲＬを使えばいいってことね。
[![graph](https://mackerel.io/embed/public/embed/dL0Cd85SJKpO1huYMDwLzbJEWHL75IaFTI4RUHtl8xD95kbG0nUnms27sGXMGT95.png?period=1h)](https://mackerel.io/orgs/watyanabe164/hosts/4gzbfytYgKW/-/graphs/disk#period=1h)

# 結論
オーガニゼーションに所属している人同士でやるなら「リンク」のURLが一番見やすいねってことがよくわかりました。
[Android] Realmで部分一致検索、前方一致検索、後方一致検索をしたい。

# はじめに
Realmでのデータの検索時、EqualToしか知らなくて、検索がとてもシビアになってしまっていませんか？
検索の幅を広げるためにも、様々な検索の仕方をまとめてみました。
今回は文字型だけ集めてみました。

# 検索方法
## 一致検索

```Kotlin
realm.where(データクラス::class.java)
                .equalTo("フィールド名",word)
                .findAll()

```

引数：
fieldName -比較するフィールド。
value -比較する値。

##非一致検索

```Kotlin
realm.where(データクラス::class.java)
                .notEqualTo("フィールド名",word)
                .findAll()

```

引数：
fieldName -比較するフィールド。
value -比較する値。

## 部分一致検索

```Kotlin
realm.where(データクラス::class.java)
                .contains("フィールド名",word)
                .findAll()

```

引数：
fieldName -比較するフィールド。
value -比較する値。

## 前方一致検索

```Kotlin
realm.where(データクラス::class.java)
                .beginWith("フィールド名",word)
                .findAll()

```

引数：
fieldName -比較するフィールド。
value -比較する値。

## 後方一致検索

```Kotlin
realm.where(データクラス::class.java)
                .extendsWith("フィールド名",word)
                .findAll()

```

引数：
fieldName -比較するフィールド。
value -比較する値。

## アンド検索

.and()の前後にある両方の条件に満たすものだけを集める物

```Kotlin
realm.where(データクラス::class.java)
                .contains("フィールド名",word)
                .and()
                .contains("フィールド名",word)
                .findAll()

```

引数：
fieldName -比較するフィールド。
value -比較する値。

## オア検索

.or()の前後にある両方の条件に少なくとも１つは満たすものを集める

```Kotlin
realm.where(データクラス::class.java)
                .contains("フィールド名",word)
                .or()
                .contains("フィールド名",word)
                .findAll()

```

引数：
fieldName -比較するフィールド。
value -比較する値。

# 参考資料

https://docs.mongodb.com/realm-legacy/docs/java/latest/api/io/realm/RealmQuery.html#greaterThan-java.lang.String-int-

http://challenge.no1s.biz/programming/242
すでにあるレコードの特定のカラムの値をNULL保存したい時（Laravel）

プログラミング初心者です

##解決したい問題
```user table```の中に```player_id```というカラムがあります。
```player_id```カラムをだけ指定して、削除したく```whereメソッド```とか使ってみたんですが、レコードが削除されてユーザー情報自体が消えてしまいました。

##解決方法
なので削除という考えはダメだと思い、NULLにすればいいのでは？と思いついたので、このコードを書いてみました。

```Controller.php
//actionの中に書きます
$user = Auth::user();
        if ($user->player_id != NULL) {
            $user->player_id = NULL;
            $user->save();

        }
```
##流れ
①Authを使ってユーザー情報を取得（User Modelじゃないのは今ログインしてるユーザーのplayer_idをNULLにしたいから）
②「もしuser tableのplayer_idがNULLじゃなかったら」のif文書きます
③NULLじゃなかったらplayer_idにNULLを代入、保存

##備考
migration作成時にNULLを保存(```->nullable(true)```)できる様にしないとNULL保存できないのでご注意を。
アセンブラで覗くコンピュータの本質

こんにちは。Ultimatrustの清水です。

突然ですが、Ultimatrustは中途入社のエンジニアが多く、個々人が持っている技術的なスキルも様々です。

私は元々PC向けセキュリティソフトの開発エンジニアでした。そしてその当時の開発言語は**アセンブラ**です。

アセンブラで開発していましたと言うと、大体2通りの反応が返ってきます。

①「アセンブラって何ですか？？？？」
②「懐かしいなぁ、俺の若いころは～・・・」

この反応からもわかる通り、現在のアプリ開発の現場でアセンブラを目にする機会はほとんどありません。

しかし、実はこの言語を理解すると、コンピュータの仕組みについてより深く知ることができます。（正確に言えば、コンピュータの仕組みを理解していないとアセンブラでのプログラミングは難しいと思っています。）

この記事では主に①の反応をされた方々に向けて、**アセンブラとは何か**を簡潔にご紹介しようと思います。②の反応をされた（素敵な）おじさま方は、ぜひ懐かしさを感じながらあの素晴らしい言語を一緒に振り返っていきましょう。

## プログラムの実行

アセンブラを理解するにあたりまず初めに覚えるべきことは、**コンピュータがどのようにプログラムを実行しているか**ということです。

当然ですが、コンピュータは人間の言葉を理解できません。現在の一般的なコンピュータが処理できるのは0または1の2進数で表現された命令だけです（これを機械語といいます）。この2進数で記述された命令を電気信号として送信することで、コンピュータは様々なデバイスを制御しています。

しかし、人間が2進数で直接命令を記述することは現実的ではありません。そこで、より人間が理解しやすいよう人間の言葉に近い表現で記述できるプログラミング言語や、その言語をコンピュータが理解できるように変換するプログラム（コンパイラ）が開発されてきました。

こういった経緯があって、現代ではPythonやJavaなどのいわゆる高級言語を用いてプログラミングができるようになっています。

## アセンブラとは

プログラムを読み込んで実行するのはCPUの役目です。CPUはプログラムに記述された命令を1つずつ解釈し実行します。

アセンブラは、**CPUが発行する命令単位でプログラムできる言語**です。高級言語では複数のCPU命令がまとまって1つの関数のように扱われますが、アセンブラでは1つの命令がそのままCPUの1つの命令に相当します。

つまり、アセンブラでプログラミングを行う際には、CPUがある命令を出すとそのほかのコンピュータリソースにどう影響するかを理解している必要があります。

## Hello, World

では、実際にアセンブラがどれだけ他の言語と違うのかについて、定番のHello Worldを例に見ていきましょう。
※アセンブラでは取り扱うCPUやOSによって記法や命令セットが異なりますので、ここではLinux OSを前提とした一例とご理解ください。

まず、Python（厳密にはPython3）でのHello World標準出力では以下のコードを実行します。

1. print(Hello, World)

このコードはprintという関数が英語で直感的に理解できることから、プログラミングをしたことがない方でも理解しやすいコードになっています。（これがいわゆる高級言語の特徴ともいえます。）

では、同じ内容をアセンブラで記述してみます。

1. hello: db Hello, World
2. mov rax, 1
3. mov rdi, 1
4. mov rsi, hello
5. mov rdx, 12
6. syscall
7. mov rax, 60
8. xor rdi, rdi
9. syscall

初めてアセンブラのコードを見た方は何が何やらわからないと思いますので、それぞれ簡単に解説していきます。

1行目のdbはそれに続く文字列をASCIIコードに変換し、数値としてラベル（ここではhello）が示すアドレスに書き込んでいます。（helloラベルは書き込んだデータの先頭アドレスを指している、C言語で言うところのポインタのようなものです。）

次に2行目ですが、アセンブラでの演算は基本的に全て**レジスタ**と呼ばれるCPU内部の記憶装置で行われます。上記のコードに出てくるrax、rdi、rsiなどがレジスタです。

movは値をコピーするコマンドです。左側で指定したレジスタに右側で指定した値を代入するために利用します。

つまり2～5行目ではそれぞれレジスタraxに1、rdiに1、rsiに出力したいデータの参照先アドレス、そしてrdxに13を代入しています。

ラベルの中身は出力したい文字列なのでrsiはなんとなくわかると思いますが、それ以外のmovコマンドは何をしているかこれだけでは意味が分かりません。

実は、ここでは6行目の**syscallコマンド**で必要な情報を格納しています。

syscallコマンドは**OSカーネルの機能呼び出しを実行するためのコマンド**です。このコマンドでは特定のレジスタの値が発行される命令のパラメータになっています。

2行目で指定したraxの値「1」は**write命令**を指定しており、ファイルディスクリプタによって指定された出力先に書き込みを行います。ファイルディスクリプタはrdiの値に従い、ここでは「1」の標準出力が指定されています。rdxでは書き込むデータのバイト数を指定します。ここではHello, Worldの文字列を出力したいので12バイトを指定します。

ここまでで標準出力が完了しましたが、最後の3行でもう一度syscallを発行しています。

これはraxで60が指定されており、**exit命令**を意味します。同じsyscallコマンドでもraxの値によって先ほどのwriteコマンドとは別の命令が発行されるわけです。

xorコマンドは2つのレジスタの排他的論理和を左のレジスタに返すため、ここではレジスタrdiをクリアする意味を持ちます。

これで、晴れてアセンブラプログラミングによるHello World出力が完成しました。

## アセンブラを学ぶ意味

いかがでしょうか？この例を見ると、今の時代に通常のアプリ開発でアセンブラが利用されない理由も何となくわかるかと思います。Pythonだとわずか1行で済むコードにこれだけの理解が必要では、学習コストも高く開発の効率が悪いのは事実です。

現代ではコンピュータリソースが豊富に確保できるため、厳密なメモリ管理やsyscall単位での効率化を意識する必要性が薄れていることもあり、今後ますますアセンブラを知るエンジニアは減っていくのではないかと思います。

しかしその一方で、技術者としてはアセンブラプログラミングを学ぶことがCPUアーキテクチャやOS機能などコンピュータの本質を理解する一助になると考えています。

もちろん、省リソースでの組み込みプログラムやOSブートローダなど低レイヤの開発では現在でもアセンブラのスキルは必須です。こういった開発に携わりたい方はぜひアセンブラを学びましょう。

今回の記事で少しでもアセンブラに興味を持ってくださった方は、簡単なアセンブラプログラミングを学ぶとともに、今まで意識することのなかったコンピュータの本質を少し覗いてみてはいかがでしょうか？
nmcliでifIndexが変わった話

#はじめに
Qiita初めての投稿となります。お手柔らかにお願いします。。。
とりあえず少しハマったところとかのお話とか書こうかと思います。

RHEL8やCentOS8ではsysconfigではなく、NetworkManagerでのIPアドレスやルーティング情報等の設定が推奨になったかと思いますが、(7からでしたっけ、、)設定後の反映方法についてメモ。

#ハマったところ？

IPアドレスをnmcliコマンドで設定したとして、

```
# nmcli con mod eth1 ipv4.addresses 192.168.1.1/24
```

反映したい場合、以下のようにdownを実施してしまったら、

```
# nmcli con down eth1
# nmcli con up eth1
```

downの際にeth1のifindexが消され、upの際に別のifindexが付与されました。

#解決方法
IPアドレスの変更くらいだったら、downせずにupだけ、もしくはNetworkMangerサービスの再起動でも反映可能。
全部の設定についてupとかサービス再起動で反映できるかは不明。。
WSL2上でTypeScriptやJavaScriptの補完が効かない時の対処法

# 環境
WSL2 Ubuntu-20.04
エディタ　VSCode
シェルをfishからbashに変更（関係ないかもしれない）

ここからが重要
vscodeのEmmetのsetting.jsに以下を追加する

```setting.json
{
...
    "emmet.syntaxProfiles": {
        "javascript": "jsx",
        "typescript": "tsx"
    },
    "emmet.triggerExpansionOnTab": true
}
```

これで自分の環境では補完が効くようになった。
【キャッチアップ】circleCI

### config.ymlの書き方が肝
- CLIを使ってバリデーションを行う
https://circleci.com/docs/ja/2.0/local-cli/
- SSHビルドで試行する
https://circleci.com/docs/ja/2.0/ssh-access-jobs/

最小限の内容のymlからスタートして、試行しながら複雑に、早くしていく。()
最初からいろいろ書いてCI実行していると時間がかかる。

## 【参考】入門的な動画
https://www.youtube.com/watch?v=iji-TtKPV0U

https://www.youtube.com/watch?v=lZD1MIHwMBY&t=11568s
bundle exec rails new ~~~  -d postgresql -f でエラーが出たとき

dbをpostgresqlを使おうとして『rails new　〜〜』をしようとしたら  

<pre>
bundler: failed to load command: rails 

can't find executable rails for gem railties. railties is not currently included in the bundle, perhaps you meant to add it to your Gemfile?
</pre>

みたいなエラーが発生。

<h2>解決策？</h2>

やってみて解決した方法。

```ruby:コンソール
$ bundle add rails
$ bundle install --path vendor/bundle
```

上記コマンドをコンソールで入力したら解決。

<pre>bundle exec rails new アプリ名 . -d postgresql </pre>


<h2>その解決策になりそうなこと</h2>
<h3>PostgreSQLをインストール</h3>

最新のバージョンをインストール
<pre>brew install postgresql</pre>

バージョンの指定をしてインストール
<pre>brew install postgresql@10</pre>

その後にbundle installを実行
<pre>bundle install</pre>




<h2>参考サイト</h2>
https://teratail.com/questions/128059

https://sustainabilityrvl.hatenablog.com/entry/2020/03/08/231823

https://qiita.com/matcham/items/e39bf9ac787b5d8d99ef

https://qiita.com/hozmii/items/3617b67ea350f116ca3a
プログラミング初心者が挑んだlaravelの検索機能追加

#今回やろうとしたこと
・投稿一覧の中から検索条件に当てはまった投稿だけ表示させたい。
・selectタグを使用した検索がしたい。
・複数条件の絞り込み。

###イメージ
formの中にselectタグを二つ用意しその値をコントローラに送りセレクト文で条件に合致する投稿だけ表示させる。

まず、検索する条件内容は変わらないのでjsonファイルに登録しておく。
*jsonファイル
 - あらかじめ決まった値を保存しておくファイル
 - https://qiita.com/shizen-shin/items/0d899fbff2c9e3ae12f4

jsonファイル

```
//今回はゲームの機材は何を使用しているのかとゲームの実力（ランク帯）を条件に検索する
{
	"machine":{
		"PC" : "PC",
		"PS4" : "PS4"
	},
	"lank":{
		"champion" : "チャンピオン",
		"dia" : "ダイア",
		"platina" : "プラチナ",
		"gold" : "ゴールド",
		"silver" : "シルバー",
		"bronze" : "ブロンズ",
		"copper" : "コッパー"
	}
}
```

続いてControllerを書いていく。

```
public function search(Request $request){

			// 絶対パスでjsonファイルを指定する
			$url = public_path() ."/json/machin.json";

			// jsonファイルのデータをとってきて$jsonに代入
			$json = file_get_contents($url);
		
			// $json（連想配列）の中身が文字化けしないようにする
			$json = mb_convert_encoding($json, 'UTF8', 'ASCII,JIS,UTF-8,EUC-JP,SJIS-WIN');
		
			// 第二引数のturuを指定することで連想配列にする
			$arr = json_decode($json,true);	

	}
```

一旦jsonファイルの中身をController側で取得する処理を書く
続いてviewのform部分を記載していくが、まず下記の認識を合わせておく
①$arrにはjsonファイルに保存しておいたmachineとlankの連想配列がそれぞれ入っている。
②ユーザーが条件を指定しないで検索する場合があるので、その場合は両方のセレクトタグに全選択を用意してあげてvalueにはallを指定しておく。
そうすることで何も指定しなかった場合にはmachineとlankにallの値が入る。

```
    <form action="{{ route('posts.search') }}">
      <select name="machine">
        <option value="all">全選択</option>
        @foreach($arr["machine"] as $key => $value)
        {{-- machineの連想配列のkeyに入っている値を$valueとして回す --}}
          <option value="{{ $value }}">{{ $value }}
          </option>
        @endforeach
      </select>

      <select name="lank">
        <option value="all">全選択</option>
        @foreach($arr["lank"] as $key => $value)
        {{-- lankの連想配列のkeyに入っている値を$valueとして回す --}}
          <option value="{{ $value }}">{{ $value }}
          </option>
        @endforeach
      </select>
      <button class="aaa" type="submit">検索する</button>
    </form>
```

viweは完成！！
Controllerに戻りif文のところから追記
まず条件に以下の3点が発生することを想定している
①条件なし
②machineの条件だけ選択されてlankの条件は選択されない（all）
③lankの条件だけ選択されてのmachine条件は選択されない（all）

```
public function search(Request $request){

			// 絶対パスでjsonファイルを指定する
			$url = public_path() ."/json/machin.json";

			// jsonファイルのデータをとってくる
			$json = file_get_contents($url);
		
			// 連想配列の中身が文字化けしないようにする
			$json = mb_convert_encoding($json, 'UTF8', 'ASCII,JIS,UTF-8,EUC-JP,SJIS-WIN');
		
			// 第二引数のturuを指定することで連想配列にする
			$arr = json_decode($json,true);	

ーーーーーーーーーーーーーーーー下記を追記ーーーーーーーーーーーーーー

		if($request->machine == $request->lank){
			// 両方指定されていなければ全ての投稿をとってくる。
			$posts = Post::get();

		}elseif($request->lank == 'all'){

			// lankが指定されていなければmachineの選択条件と一致したやつをとってくる
			$posts = Post::where('message',$request->machine)->get();

		}elseif($request->machine == 'all'){

			// machineが指定されていなければlankの選択条件と一致したやつをとってくる
			$posts = Post::where('grade',$request->lank)->get();
			
		}else{
			$posts = Post::where('grade',$request->lank)->where('message',$request->machine)->get();	
		}
		$userId = Auth::id();

		return view('posts.index', compact('posts','userId','arr'));
	}
```

上記の方法で条件検索処理ができた。
初心者なので説明が下手くそだけどとりあえずコピペして試してみてね。
【キャッチアップ】React

### jsx
```
<React.Fragment>
</React.Fragment>
```
不要なdivタグを使わずにコンポーネントを書く方法

### 環境構築については以下記事を参照させていただきました。
https://qiita.com/ohs30359-nobuhara/items/bdc06b2db1bef7af2439

### reactドキュメント
https://ja.reactjs.org/

### nodesドキュメント
https://nodejs.org/ja/docs/

### expressドキュメント
https://expressjs.com/

### material-uiドキュメント
https://material-ui.com/ja/getting-started/installation/

### babelドキュメント
https://babeljs.io/docs/en/

### webpackドキュメント
https://webpack.js.org/

### jestドキュメント
https://jestjs.io/ja/docs/getting-started

### dockerizing-a-react-application-with-nodejs-postgres-and-nginx
https://lebersoftware.hu/dockerizing-a-react-application-with-nodejs-postgres-and-nginx-dev-and-prod-step-by-step-tutorial/

https://gitlab.com/codeching/docker-multicontainer-application-react-nodejs-postgres-nginx-basic

### 【参考】browselify/babelifyを使ったビルド
https://qiita.com/mizumizue/items/b800e0828674d8602b1a

### 【参考：入門動画】
https://www.youtube.com/watch?v=Ym4If5W9SS0&list=PLX8Rsrpnn3IWPoM7-1YPDksRRkamRY25k
カラム名にSQLで使われる単語を設定した時のorderの仕方

※コードは簡易的に書いています。

##はじめに
ListテーブルとCardテーブルが一対多の関係で作成してあり、
Cardテーブルのorderカラムにはcard、作成時に指定した表示位置の順番が入っています。(1が入っていれば1番上に表示)

```ruby
class Card < ApplicationRecord
  belongs_to :list
end
```

```ruby
class List < ApplicationRecord
  has_many :cards, dependent: :destroy
end
```

##やりたいこと
表示順をorderカラムの数値順にしたいので、list.cardsを取得したときには、orderカラムで希望した順に取得しておきたい。

```ruby
<% @lists.each do |list| %>
  <% list.cards.each do |card| %>
    <%= card.title %>
  <% end %>
<% end %>
```

##つまずいたところ
様々なサイトで調べていく中で、以下のように`has_many`に対してスコープを指定すればいいということが分かった。

```ruby
class List < ApplicationRecord
  has_many :cards, -> { order('カラム名 ASC') }, dependent: :destroy
end
```

しかし、Cardテーブルの他のカラムでは、思うように並び替えができているのに、`orderカラム`のみエラーが発生していた。


```
ActionView::Template::Error (SQLite3::SQLException: near "order": syntax error):
```

##原因
SQLの[予約語](https://www.ibm.com/docs/ja/psfa/7.1.0?topic=keywords-sql-common-reserved-words)と呼ばれるものをカラム名に使用していた事が原因だった。

##解決策
ダブルクォート("")で括むことで、並び替えて取得するようになった。

```ruby
class List < ApplicationRecord
  has_many :cards, -> { order('"order" ASC') }, dependent: :destroy
end
```


##参考サイト
[rails アソシエーション先の並べ替えを維持したい](https://ja.stackoverflow.com/questions/43921/rails-%E3%82%A2%E3%82%BD%E3%82%B7%E3%82%A8%E3%83%BC%E3%82%B7%E3%83%A7%E3%83%B3%E5%85%88%E3%81%AE%E4%B8%A6%E3%81%B9%E6%9B%BF%E3%81%88%E3%82%92%E7%B6%AD%E6%8C%81%E3%81%97%E3%81%9F%E3%81%84)
[[ Oracle ] テーブル名やカラム名にSQL予約語を使用する](https://hensa40.cutegirl.jp/archives/1259)
[SQL の一般的な予約語](https://www.ibm.com/docs/ja/psfa/7.1.0?topic=keywords-sql-common-reserved-words)
追加したカラムに既存のカラムの値を指定する

地道にやりましょう。

```sql
ALTER TABLE my_table
ADD COLUMN new_column VARCHAR(255);

UPDATE my_table SET new_column = old_column
WHERE new_column IS NULL;
```

既存のカラムを消したければ。

```sql
ALTER TABLE my_table
DROP COLUMN old_column CASCADE;
```

おわり。
【Flutter】画面遷移しながらアニメーションさせる方法【Hero】

##基本的なやりかた
2つの画面（遷移元と遷移先）にHeroウィジェットを設置し、tagというプロパティをそれぞれにつけるだけ。
tagは一致させる必要がある。

##必要なもの
Heroウィジェット×２
（遷移元の画面、遷移先の画面にそれぞれひとつずつ）

tagプロパティ
(Heroクラスで唯一必須のプロパティ)

```dart
import 'package:flutter/material.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Heroアニメーション',
      home: FirstScreen(),
    );
  }
}

class FirstScreen extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Main Screen'),
      ),
      body: GestureDetector(
        onTap: () {
          Navigator.push(context, MaterialPageRoute(builder: (_) {
            return SecondScreen();
          }));
        },
        child: Hero(
          tag: 'imageHero', //必須のプロパティ（遷移先と合わせる）
          child: FlutterLogo(
            size: 50,
          ),
        ),
      ),
    );
  }
}

class SecondScreen extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Scaffold(
      body: GestureDetector(
        onTap: () {
          Navigator.pop(context);
        },
        child: Center(
          child: Hero(
            tag: 'logo', //必須のプロパティ（遷移元と合わせる）
            child: FlutterLogo(
              size: 100, //アニメーションさせたいプロパティの値を、遷移元と変えておく
            ),
          ),
        ),
      ),
    );
  }
}
```

##結果

画面を遷移させると、左上にあったロゴがアニメーションしながら拡大されて、中央に配置されるはずです。

![hero1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/455043/270f2612-1cb2-fbf1-8e49-eecd052c3b4f.png)

![hero2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/455043/826e3e0b-999b-ac5a-b5be-21fd8e7fa1af.png)


<a href="https://www.buymeacoffee.com/neruk" target="_blank"><img src="https://cdn.buymeacoffee.com/buttons/v2/default-yellow.png" width=200></a>