【Salesforce】郵便番号から住所検索して自動入力【LWC】

photo of nimbus clouds Lightning Web Component
Photo by Josh Sorenson on Pexels.com

今回は、レコードの作成画面等で、郵便番号から住所を自動入力したい

という要望を LWC で実現しました。

住所検索コンポーネントの作成

複数の画面で汎用的に使えるようコンポーネント化します。

入力(@api をつけた変数)として郵便番号を受け取り、ボタンクリック時に住所情報をイベントとして発信します。

<template>
    <lightning-button label="住所検索" onclick={search}></lightning-button>
    <template if:true={isError}>
        <!-- コンポーネントを狭い場所に配置しても良いように、エラー文もなるべく短くしている -->
        <div class="slds-text-color_error">検索エラー</div>
    </template>
</template>
import { api, LightningElement } from 'lwc';
import getAddress from '@salesforce/apex/ZipCloudAPI.getAddress';

export default class AddressSearch extends LightningElement {
    @api postalCode;
    isError = false;

    search() {
        getAddress({ zipcode: this.postalCode })
            .then(result => {
                const resultList = result.results;
                if (result.status === 200 && resultList != null) {
                    this.isError = false;
                    let addressInfo = {};
                    addressInfo.prefecture = resultList[0].address1;
                    if (resultList.length === 1) {
                        addressInfo.address = resultList[0].address2 + resultList[0].address3;
                    } else {
                        // 検索結果が複数あっても、address2 の値までは一致している
                        addressInfo.address = resultList[0].address2;
                    }
                    const e = new CustomEvent('clickbutton', { detail: addressInfo });
                    this.dispatchEvent(e);
                } else {
                    this.isError = true;
                }
            })
    }
}

実際に郵便番号を取得する部分は zipcloud というサービスを利用しています。

また、コンポーネントから getAddress という Apex メソッドを呼び出しているのですが、以下の注意点があります。

  • LWCで参照する Apexメソッド、内部クラスの変数に @AuraEnabled をつける
  • @AuraEnabled をつけたメソッドにアクセスする場合、(プロファイル等で)クラスに対する権限を付与する必要がある
  • 設定 → リモートサイトの設定で、https://zipcloud.ibsnet.co.jp を登録しておく
public with sharing class ZipCloudAPI {
    public class Response {
        @AuraEnabled public Integer status;
        @AuraEnabled public String message;
        @AuraEnabled public List<Map<String, String>> results;
    }

    @AuraEnabled
    public static Response getAddress(String zipcode){
        String endPoint = 'https://zipcloud.ibsnet.co.jp/api/search?zipcode=' + zipcode;
        HttpRequest request = new HttpRequest();
        request.setEndpoint(endPoint);
        request.setMethod('GET');
        request.setHeader('Content-Type','application/json');

        Http http = new Http();
        HttpResponse res = http.send(request);
        return (Response)JSON.deserializeStrict(res.getBody(), Response.class);
    }
}

住所検索コンポーネントの使用例

上記で作成した住所検索コンポーネントを、別のコンポーネントから呼び出します。
以下は例として作成したデモ画面です。
アクションボタンから呼び出すような(lightning-quick-action-panel)画面になっています。

<template>
    <lightning-record-edit-form object-api-name="Account">
        <lightning-quick-action-panel header="住所検索デモ">
            <div class="slds-grid slds-wrap">
                <div class="slds-col slds-size_2-of-3 slds-p-horizontal_small">
                    <lightning-input type="text" label="郵便番号" variant="standard" class="postalcode" onchange={handleChange}></lightning-input>
                </div>
                <div class="slds-col slds-size_1-of-3 slds-m-top_large">
                    <c-address-search onclickbutton={setAddress} postal-code={postalCodeValue}></c-address-search>
                </div>
                <div class="slds-col slds-p-horizontal_small">
                    <lightning-input type="text" label="都道府県" value={prefecture} variant="standard" class="prefecture"></lightning-input>
                    <lightning-input type="text" label="住所" value={address} variant="standard" class="address"></lightning-input>
                </div>
            </div>
            <div slot="footer">
                <lightning-button variant="brand" label="保存" class="slds-m-left_x-small" type="submit" disabled={disabled}></lightning-button>
            </div>
        </lightning-quick-action-panel>
    </lightning-record-edit-form>
</template>
import { LightningElement } from 'lwc';

export default class addressSearchDemo extends LightningElement {
    postalCodeValue;
    handleChange(){
        this.postalCodeValue = this.template.querySelector('.postalcode')?.value;
    }

    setAddress(event) {
        this.template.querySelector('.prefecture').value = event.detail.prefecture;
        this.template.querySelector('.address').value = event.detail.address;
    }
}
<?xml version="1.0" encoding="UTF-8"?>
<LightningComponentBundle xmlns="http://soap.sforce.com/2006/04/metadata">
    <apiVersion>54.0</apiVersion>
    <isExposed>true</isExposed>
    <targets>
        <target>lightning__RecordAction</target>
    </targets>
    <targetConfigs>
        <targetConfig targets="lightning__RecordAction">
            <actionType>ScreenAction</actionType>
        </targetConfig>
    </targetConfigs>
</LightningComponentBundle>

コメント

タイトルとURLをコピーしました