お知らせ:

当社は、お客様により充実したサポート情報を迅速に提供するため、本ページのコンテンツは機械翻訳を用いて日本語に翻訳しています。正確かつ最新のサポート情報をご覧いただくには、本内容の英語版を参照してください。

Functionsディレクトリの設定

次に、Functionsを設定してMuseum Finderアプリケーションのコーディングを開始します。

4つのJava Functionsはすべて、それぞれのFunctionディレクトリに以下のファイルを含みます:

  • メインJava Functionファイル
  • catalyst-config.json設定ファイル
  • JARライブラリファイル
  • .classpathおよび.project依存関係ファイル

Node.js Functionは、そのディレクトリに以下のファイルを含みます:

  • index.jsメインFunctionファイル
  • catalyst-config.json設定ファイル
  • Nodeモジュール
  • package.jsonおよびpackage-lock.json依存関係ファイル

各Java FunctionのメインJavaファイルと、Node.js Functionのindex.jsファイルにコードを追加します。

Functionの設定には任意のIDEを使用できます。

Note: このセクションのコードを十分に理解するために、必ず目を通してください。セクションの最後でFunctionsのコードについて説明します。

以下のコードをコピーして、functions/RatingProcessorディレクトリにあるRatingProcessor.javaに貼り付けて、ファイルを保存します。

RatingProcessor.java
copy
import com.catalyst.Context;
import com.catalyst.basic.BasicIO;
import com.catalyst.basic.ZCFunction;
import com.fasterxml.jackson.databind.ObjectMapper;
import java.util.logging.Logger;
import org.json.simple.JSONObject;
import org.json.simple.parser.JSONParser;
import java.io.File;
import java.io.FileReader;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashMap;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.logging.Level;
import com.zc.common.ZCProject;
import com.zc.component.cache.ZCCache;
import okhttp3.HttpUrl;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;
public class RatingProcessor implements ZCFunction {
 private static final Logger LOGGER = Logger.getLogger(RatingProcessor.class.getName());
 private static Map<String, Integer> map = new HashMap() { 
 	{
          put("Excellent",0); 
          put("Very good",1); 
          put("Average",2); 
          put("Poor",3);
          put("Terrible",4);
 	}
      };			
	@Override
	@SuppressWarnings("unchecked")
    public void runner(Context context, BasicIO basicIO) throws Exception {
 	try {
 		Integer topCount = 10;
 		if(basicIO.getParameter("count") != null) {
 			topCount = Integer.parseInt(basicIO.getParameter("count").toString());
 		}
 		String travellerRating = (String) basicIO.getParameter("type");
 		Integer type = 0;
 		if(travellerRating != null) {
 			if(map.containsKey(travellerRating)) {
 				type = map.get(travellerRating);
 			}
 		}
 		String url = "https://www.zoho.com/catalyst/downloads/static/tutorial/dataset/traveller-rating.json";
 		ZCProject.initProject();
 		HttpUrl.Builder httpBuilder = HttpUrl.parse(url).newBuilder();
 		OkHttpClient client = new OkHttpClient().newBuilder().build();
 		Request.Builder requestsBuilder = new Request.Builder();
 		requestsBuilder.url(httpBuilder.build());
 		requestsBuilder.get();
 		Response responses = client.newCall(requestsBuilder.build()).execute();
 		String responsebody = responses.body().string();
 		JSONParser parser = new JSONParser();
 		JSONObject dataJSON = (JSONObject) parser.parse(responsebody);
 		HashMap<String, Long> execellentRating = new HashMap<>();
 		Iterator<String> itrJson = dataJSON.keySet().iterator();
 		while(itrJson.hasNext()) {
 			String museumName = itrJson.next();
 			List<String> ratingList = new ObjectMapper().convertValue(dataJSON.get(museumName), List.class);
 			Long exellentRating = Long.parseLong(ratingList.get(type));
 			execellentRating.put(museumName, exellentRating);
 		}
 		execellentRating = RatingProcessor.sortByValue(execellentRating);
 		List<String> execellentMuseum = new ArrayList<>();
 		itrJson = execellentRating.keySet().iterator();
 		Integer i= 0;
 		while(i++ < topCount && itrJson.hasNext()) {
 			execellentMuseum.add(itrJson.next());
 		}
 		basicIO.write(new ObjectMapper().writeValueAsString(execellentMuseum));
 	}
 	catch(Exception e) {
 		LOGGER.log(Level.SEVERE,"Exception in RatingProcessor",e);
 		basicIO.setStatus(500);
 	}
 }
 public static HashMap<String, Long> sortByValue(HashMap<String, Long> hm) 
    { 
        // HashMapの要素からリストを作成
        List<Map.Entry<String, Long> > list = 
               new LinkedList<Map.Entry<String, Long> >(hm.entrySet()); 
        // リストをソート
        Collections.sort(list, new Comparator<Map.Entry<String, Long> >() { 
            public int compare(Map.Entry<String, Long> o1,  
                               Map.Entry<String, Long> o2) 
            { 
                return (o2.getValue()).compareTo(o1.getValue()); 
            } 
        }); 
        // ソートされたリストのデータをHashMapに格納
        HashMap<String, Long> temp = new LinkedHashMap<String, Long>(); 
        for (Map.Entry<String, Long> aa : list) { 
            temp.put(aa.getKey(), aa.getValue()); 
        } 
        return temp; 
    } 
 }

View more


以下のコードをコピーして、functions/TravellerTypeRatingProcessorディレクトリにあるTravellerTypeRatingProcessor.javaに貼り付けて、ファイルを保存します。

TravellerTypeRatingProcessor.java
copy
import java.io.File;
import java.io.FileReader;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashMap;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.json.simple.JSONObject;
import org.json.simple.parser.JSONParser;
import com.catalyst.Context;
import com.catalyst.basic.BasicIO;
import com.catalyst.basic.ZCFunction;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.zc.common.ZCProject;
import okhttp3.HttpUrl;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;
public class TravellerTypeRatingProcessor implements ZCFunction {	
	private static final Logger LOGGER = Logger.getLogger(TravellerTypeRatingProcessor.class.getName());	
	private static Map<String, Integer> map = new HashMap() { 
		{
          put("Families",0); 
          put("Couples",1); 
          put("Solo",2); 
          put("Business",3);
          put("Friends",4);
		}
      };	
	@Override
    public void runner(Context context, BasicIO basicIO) throws Exception {
		try {			
			Integer topCount = 10;
			String travellerType = (String) basicIO.getParameter("type");
			Integer type = 0;
			if(travellerType != null) {
				if(map.containsKey(travellerType)) {
					type = map.get(travellerType);
				}
			}
			if(basicIO.getParameter("count") != null) {
				topCount = Integer.parseInt(basicIO.getParameter("count").toString());
			}
			String url = "https://www.zoho.com/catalyst/downloads/static/tutorial/dataset/traveller-type-rating.json";
			ZCProject.initProject();
			HttpUrl.Builder httpBuilder = HttpUrl.parse(url).newBuilder();
			OkHttpClient client = new OkHttpClient().newBuilder().build();
			Request.Builder requestsBuilder = new Request.Builder();
			requestsBuilder.url(httpBuilder.build());
			requestsBuilder.get();
			Response responses = client.newCall(requestsBuilder.build()).execute();
			String responsebody = responses.body().string();
			JSONParser parser = new JSONParser();
			JSONObject dataJSON = (JSONObject) parser.parse(responsebody);
			HashMap<String, Long> execellentRating = new HashMap<>();		
			Iterator<String> itrJson = dataJSON.keySet().iterator();
			while(itrJson.hasNext()) {		
				String museumName = itrJson.next();
				List<String> ratingList = new ObjectMapper().convertValue(dataJSON.get(museumName), List.class);
				Long rating = Long.parseLong(ratingList.get(type));
				execellentRating.put(museumName, rating);
			}
			execellentRating = TravellerTypeRatingProcessor.sortByValue(execellentRating);
			List<String> execellentMuseum = new ArrayList<>();
			itrJson = execellentRating.keySet().iterator();
			Integer i= 0;
			while(i++ < topCount && itrJson.hasNext()) {
				execellentMuseum.add(itrJson.next());
			}
			basicIO.write(new ObjectMapper().writeValueAsString(execellentMuseum));
		}
		catch(Exception e) {
			LOGGER.log(Level.SEVERE,"Exception in TravellerTypeRatingProcessor",e); // このログはCatalystコンソールのLogsから確認できます
			basicIO.setStatus(500);
		}
	}
	public static HashMap<String, Long> sortByValue(HashMap<String, Long> hm) 
    { 
        // HashMapの要素からリストを作成
        List<Map.Entry<String, Long> > list = 
               new LinkedList<Map.Entry<String, Long> >(hm.entrySet()); 
        // リストをソート
        Collections.sort(list, new Comparator<Map.Entry<String, Long> >() { 
            public int compare(Map.Entry<String, Long> o1,  
                               Map.Entry<String, Long> o2) 
            { 
                return (o2.getValue()).compareTo(o1.getValue()); 
            } 
        }); 
        // ソートされたリストのデータをHashMapに格納
        HashMap<String, Long> temp = new LinkedHashMap<String, Long>(); 
        for (Map.Entry<String, Long> aa : list) { 
            temp.put(aa.getKey(), aa.getValue()); 
        } 
        return temp; 
    } 	
}

View more


以下のコードをコピーして、functions/MergeDataSetディレクトリにあるMergeDataSet.javaに貼り付けて、ファイルを保存します。

MergeDataSet.java
copy
import com.catalyst.Context;
import com.catalyst.basic.BasicIO;
import com.catalyst.basic.ZCFunction;
import com.fasterxml.jackson.databind.ObjectMapper;
import java.util.logging.Logger;
import org.json.simple.JSONArray;
import org.json.simple.JSONObject;
import java.util.ArrayList;
import java.util.List;
import java.util.logging.Level;
import com.zc.common.ZCProject;
import com.zc.component.cache.ZCCache;
import com.zc.component.object.ZCTable;
public class MergeDataSet implements ZCFunction {
	private static final Logger LOGGER = Logger.getLogger(MergeDataSet.class.getName());
	@Override
    public void runner(Context context, BasicIO basicIO) throws Exception {
		try {
			Object ratingList = basicIO.getArgument("rating_list");
			Object typeRatingList = basicIO.getArgument("traveller_type_rating_list");
			ObjectMapper mapper = new ObjectMapper();
			List<String> travellerRatingList = mapper.readValue(ratingList.toString(), mapper.getTypeFactory().constructCollectionType(List.class, String.class));;
			List<String> travellerTypeRatingList = mapper.readValue(typeRatingList.toString(), mapper.getTypeFactory().constructCollectionType(List.class, String.class));;
			List<String> finalList = new ArrayList<>();
			for(int i=0 ; i< travellerTypeRatingList.size() ; i++) {
				if(travellerRatingList.contains(travellerTypeRatingList.get(i))) {
					finalList.add(travellerTypeRatingList.get(i).toString());
				}
			}
			JSONObject respJson = new JSONObject();
			respJson.put("museum_list", finalList);
			LOGGER.log(Level.INFO, "Museum Count"+finalList.size()); // このログはCatalystコンソールのLogsから確認できます
			basicIO.write(new ObjectMapper().writeValueAsString(respJson));
		}
		catch(Exception e) {
			e.printStackTrace();
			LOGGER.log(Level.SEVERE,"Exception in MergeDataSet",e); // このログはCatalystコンソールのLogsから確認できます
			basicIO.setStatus(500);
		}
	}
}

View more


以下のコードをコピーして、functions/MailerディレクトリにあるMailer.javaに貼り付けて、ファイルを保存します。

Mailer.java
copy
import java.util.logging.Level;
import java.util.logging.Logger;

import org.json.simple.JSONObject;

import com.catalyst.Context; import com.catalyst.basic.BasicIO; import com.catalyst.basic.ZCFunction; import com.zc.common.ZCProject; import com.zc.component.mail.ZCMail; import com.zc.component.mail.ZCMailContent;

public class Mailer implements ZCFunction {

private static final Logger LOGGER = Logger.getLogger(Mailer.class.getName());

private static final String SUBJECT = "Museum Search Results";

private static final String FROM_MAIL = "emma@zylker.com"; // 先ほど設定した送信者のメールアドレスを入力してください

@Override
public void runner(Context context, BasicIO basicIO) throws Exception {
	try {
		ZCProject.initProject();
		Object content = basicIO.getArgument("content"); // MergeDataSet Functionから最終リストを取得
		Object mailId = basicIO.getArgument("mail_id"); // 提供された入力からユーザーのメールアドレスを取得
		if(content != null) {
			
			String mailContent = content.toString();
			ZCMailContent mail = ZCMailContent.getInstance();
			mail.setSubject(SUBJECT);
			mail.setFromEmail(FROM_MAIL);
			if(mailId != null) {
				mail.setToEmail(mailId.toString());
			}
			else {
				basicIO.write(constructErrorMessage("mail_id not found"));
				basicIO.setStatus(400);
				return;
			}
			mail.setContent(mailContent);
			mail.setHtmlMode(false);
			ZCMail.getInstance().sendMail(mail);
			basicIO.setStatus(200);
			basicIO.write(constructSuccessMessage("Mail has been sent to "+mailId+" successfully"));
		}
	}
	catch(Exception e) {
		LOGGER.log(Level.SEVERE,"Exception in Mailer",e); // このログはCatalystコンソールのLogsから確認できます
		basicIO.setStatus(500);
		basicIO.write(constructErrorMessage(e.getMessage()));
	}
}

private JSONObject constructErrorMessage(String message) {
	
	JSONObject errorJSON = new JSONObject();
	errorJSON.put("status", "failure");
	errorJSON.put("message", message);
	return errorJSON;
}

private JSONObject constructSuccessMessage(String message) {
	
	JSONObject errorJSON = new JSONObject();
	errorJSON.put("status", "success");
	errorJSON.put("message", message);
	return errorJSON;
}

}

View more

Note: 先ほど設定した送信者のメールアドレスを19行目に入力してください。

Expressのインストール

Node.js Functionのコーディングを行う前に、ディレクトリにExpress Node.jsの依存関係をインストールする必要があります。

ローカルマシンにExpress.jsをインストールするには、ターミナルでFunctionのディレクトリ(functions/circuit)に移動し、以下のコマンドを実行します:

copy
$
npm install express --save

これにより、Expressモジュールがインストールされ、依存関係が保存されます。

この情報はpackage.jsonファイルにも更新されます。


次に、index.jsファイルをコーディングしましょう。

以下のコードをコピーして、functions/circuitディレクトリにあるindex.jsに貼り付けて、ファイルを保存します。

index.js
copy
'use strict';
var express = require('express');
var app = express();
var catalyst = require('zcatalyst-sdk-node');
app.use(express.json());
app.post('/triggerCircuit', (req, res) => {
	var CatalystApp = catalyst.initialize(req);
	var body = req.body;
	console.log(body);
	let execName = new Date().getTime().toString();
	console.log(execName);
	let promiseResult = CatalystApp.circuit().execute("1028000000084051",execName, body); // コンソールで作成したCircuitのCircuit IDを入力してください
	promiseResult.then((functionResponse) => {
		console.log(functionResponse);
		res.status(200).send({ message: "Please check your email for the list of museums." });
	}).catch(err => {
		console.log(err); // このログはCatalystコンソールのLogsから確認できます
		res.status(500).send({ message: "Please try again after sometime!" });
	})
});
module.exports = app;

View more

Note: CatalystコンソールでCircuitを作成した後、この Functionの14行目にCircuit IDを必ず入力してください。

設定したFunctionsについて簡単に確認しましょう。


Circuit:

  • Advanced I/O circuit Functionには、CatalystコンソールでConfigure済みのCircuitの実行をトリガーするAPI /triggerCircuitが含まれています。

    Note: Circuitは、プロジェクトリソースをリモートコンソールにデプロイした後に設定します。
  • circuit Functionは、クライアントアプリケーションでエンドユーザーから取得した入力データを、実行のトリガー時にCircuitに渡します。このデータは、クライアントディレクトリのmain.jsによってCircuit Functionに渡されます。

  • Circuitの実行が完了すると、ユーザーの条件を満たす博物館のリストをメールで確認するよう促すメッセージがクライアントアプリケーションに表示されます。このメッセージはこのFunctionで設定されています。


RatingProcessorTravellerTypeRatingProcessor:

  • RatingProcessor Functionは、博物館の以下の評価をJava HashMapに格納します:ExcellentVery GoodAveragePoorTerrible
  • TravellerTypeRatingProcessor Functionは、博物館の以下の旅行者タイプ適合性をJava HashMapに格納します:FamiliesCouplesSoloBusinessFriends
  • 評価と旅行者タイプに加えて、ユーザーは結果に表示したい博物館の数を入力します。この値はcount変数に格納され、両方のFunctionsで処理されます。
  • Functionsは、Catalystがホストするtraveller-rating.jsonまたはtraveller-type-rating.jsonデータセットをそれぞれ呼び出します。これらのデータセットには、さまざまなウェブサイトでユーザーが提供した評価や旅行者タイプの適合性のレコードが含まれています。
  • ユーザーが提供した入力に基づいて、両方のFunctionsがこれらのデータセットからレコードを取得します。例えば、ユーザーが評価タイプとしてExcellentを選択した場合、traveller-rating.jsonデータセットでその評価を持つ博物館が特定されます。ユーザーが提供したcount値を超えない範囲で、Excellent評価が最も多い博物館が降順にソートされて取得されます。ユーザーが提供した旅行者タイプの入力に一致するレコードも、同様にtraveller-type-rating.json dataset.から取得されます。
  • 両方のFunctionsが取得したレコードはJSONオブジェクトとしてパースされ、ObjectMapperクラスに書き込まれます。その後、リストでソートされ、両方のFunctionsで新しいHashMapに追加されます。

MergeDataSet:

  • MergeDataSet Functionは、RatingProcessorTravellerTypeRatingProcessor Functionsが取得したレコードを引数として受け取ります。
  • このFunctionは両方のリストの共通部分を求め、両方のリストに存在する博物館の結果を確認します。
  • 両方のリストに存在する博物館を最終リストに追加し、そのリストをJSONレスポンスとして返します。

Mailer:

  • Mailer Functionは、設定するCircuit内のMergeDataSet Functionから最終リストを取得します。これがメールの本文として設定されます。また、ユーザーが入力したメールアドレスも取得します。
  • このFunctionでメールの件名と送信者アドレスを設定できます。Mailer Functionは、取得したコンテンツを含むメールをユーザーのメールアドレスに送信します。

Functionsディレクトリの設定が完了しました。

最終更新日 2026-03-05 11:43:24 +0530 IST