├── dist └── .dist ├── public_html ├── carik │ ├── data │ │ ├── carik.dat │ │ ├── carik-group.dat │ │ ├── carik-smarthome.dat │ │ └── carik-userdata.dat │ ├── files │ │ ├── nlp │ │ │ ├── suggestion.txt │ │ │ ├── index.html │ │ │ ├── dokter-entities.txt │ │ │ ├── ai-questions.txt │ │ │ ├── dokter-intents.txt │ │ │ ├── dokter-response.txt │ │ │ ├── cs-intents.txt │ │ │ ├── cs-response.txt │ │ │ ├── ai-entities.txt │ │ │ ├── ai-intents.txt │ │ │ └── ai-response.txt │ │ ├── carik │ │ │ └── carik-userdata.dat │ │ ├── index.html │ │ ├── .htaccess │ │ ├── blacklist-global.txt │ │ └── word-nonstandard.txt │ ├── config │ │ ├── index.html │ │ ├── .htaccess │ │ └── config.json │ ├── ztemp │ │ ├── index.html │ │ ├── cache │ │ │ ├── index.html │ │ │ ├── domains │ │ │ │ ├── index.html │ │ │ │ └── .htaccess │ │ │ ├── jadwalsholat │ │ │ │ ├── index.html │ │ │ │ └── .htaccess │ │ │ └── kamus │ │ │ │ └── .htaccess │ │ ├── logs │ │ │ └── index.html │ │ ├── voice │ │ │ └── index.html │ │ ├── sessions │ │ │ └── index.html │ │ └── .htaccess │ ├── modules │ │ └── index.html │ └── .htaccess └── index.html ├── source ├── common │ ├── before.pas │ ├── loader_controller.pas │ ├── command_controller.pas │ ├── carik.inc │ ├── direct_handler.pas │ ├── facebook_handler.pas │ └── line_handler.pas ├── cli │ ├── build.sh │ ├── clean.sh │ ├── extra.cfg │ ├── carik.lpi │ └── carik.lpr ├── line │ ├── build.sh │ ├── line.res │ ├── routes.pas │ ├── clean.sh │ ├── extra.cfg │ ├── line.lpr │ ├── main.pas │ └── line.lpi ├── facebook │ ├── build.sh │ ├── facebook.res │ ├── routes.pas │ ├── clean.sh │ ├── extra.cfg │ ├── facebook.lpr │ ├── main.pas │ └── facebook.lpi ├── telegram │ ├── build.sh │ ├── telegram.res │ ├── routes.pas │ ├── clean.sh │ ├── extra.cfg │ ├── telegram.lpr │ ├── main.pas │ └── telegram.lpi ├── carik │ ├── carik.res │ ├── build.sh │ ├── routes.pas │ ├── clean.sh │ ├── extra.cfg │ ├── carik.lpr │ ├── main.pas │ └── carik.lpi └── CarikBot.lpg ├── LICENSE.txt ├── img └── compiling.png ├── Carik Bot.code-workspace ├── docker ├── build.sh ├── run.sh ├── bash.sh └── files │ ├── echo-run.sh │ └── Dockerfile ├── clean.sh ├── .gitignore └── README.md /dist/.dist: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /public_html/carik/data/carik.dat: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /public_html/index.html: -------------------------------------------------------------------------------- 1 | carik 2 | -------------------------------------------------------------------------------- /source/common/before.pas: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /public_html/carik/data/carik-group.dat: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /public_html/carik/data/carik-smarthome.dat: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /public_html/carik/data/carik-userdata.dat: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /public_html/carik/files/nlp/suggestion.txt: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /public_html/carik/files/carik/carik-userdata.dat: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /public_html/carik/config/index.html: -------------------------------------------------------------------------------- 1 | http://www.fastplaz.com 2 | -------------------------------------------------------------------------------- /public_html/carik/files/index.html: -------------------------------------------------------------------------------- 1 | http://www.fastplaz.com 2 | -------------------------------------------------------------------------------- /public_html/carik/ztemp/index.html: -------------------------------------------------------------------------------- 1 | http://www.fastplaz.com 2 | -------------------------------------------------------------------------------- /public_html/carik/files/nlp/index.html: -------------------------------------------------------------------------------- 1 | http://www.fastplaz.com 2 | -------------------------------------------------------------------------------- /public_html/carik/modules/index.html: -------------------------------------------------------------------------------- 1 | http://www.fastplaz.com 2 | -------------------------------------------------------------------------------- /public_html/carik/ztemp/cache/index.html: -------------------------------------------------------------------------------- 1 | http://www.fastplaz.com 2 | -------------------------------------------------------------------------------- /public_html/carik/ztemp/logs/index.html: -------------------------------------------------------------------------------- 1 | http://www.fastplaz.com 2 | -------------------------------------------------------------------------------- /public_html/carik/ztemp/voice/index.html: -------------------------------------------------------------------------------- 1 | http://www.fastplaz.com 2 | -------------------------------------------------------------------------------- /public_html/carik/ztemp/sessions/index.html: -------------------------------------------------------------------------------- 1 | http://www.fastplaz.com 2 | -------------------------------------------------------------------------------- /source/cli/build.sh: -------------------------------------------------------------------------------- 1 | mkdir -p lib 2 | fpc carik.lpr @extra.cfg 3 | 4 | -------------------------------------------------------------------------------- /source/line/build.sh: -------------------------------------------------------------------------------- 1 | mkdir -p lib 2 | fpc line.lpr @extra.cfg 3 | 4 | -------------------------------------------------------------------------------- /public_html/carik/ztemp/cache/domains/index.html: -------------------------------------------------------------------------------- 1 | http://www.fastplaz.com 2 | -------------------------------------------------------------------------------- /source/facebook/build.sh: -------------------------------------------------------------------------------- 1 | mkdir -p lib 2 | fpc facebook.lpr @extra.cfg 3 | 4 | -------------------------------------------------------------------------------- /source/telegram/build.sh: -------------------------------------------------------------------------------- 1 | mkdir -p lib 2 | fpc telegram.lpr @extra.cfg 3 | 4 | -------------------------------------------------------------------------------- /public_html/carik/ztemp/cache/jadwalsholat/index.html: -------------------------------------------------------------------------------- 1 | http://www.fastplaz.com 2 | -------------------------------------------------------------------------------- /LICENSE.txt: -------------------------------------------------------------------------------- 1 | 2 | Hak Cipta dilindungi Allah SWT 3 | Copyright reserved Allah SWT 4 | -------------------------------------------------------------------------------- /img/compiling.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/luridarmawan/Carik/HEAD/img/compiling.png -------------------------------------------------------------------------------- /Carik Bot.code-workspace: -------------------------------------------------------------------------------- 1 | { 2 | "folders": [ 3 | { 4 | "path": "." 5 | } 6 | ] 7 | } -------------------------------------------------------------------------------- /source/carik/carik.res: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/luridarmawan/Carik/HEAD/source/carik/carik.res -------------------------------------------------------------------------------- /source/line/line.res: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/luridarmawan/Carik/HEAD/source/line/line.res -------------------------------------------------------------------------------- /docker/build.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | echo Carik - Docker 3 | 4 | docker build -f files/Dockerfile -t carik . 5 | -------------------------------------------------------------------------------- /source/facebook/facebook.res: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/luridarmawan/Carik/HEAD/source/facebook/facebook.res -------------------------------------------------------------------------------- /source/telegram/telegram.res: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/luridarmawan/Carik/HEAD/source/telegram/telegram.res -------------------------------------------------------------------------------- /public_html/carik/files/nlp/dokter-entities.txt: -------------------------------------------------------------------------------- 1 | 2 | [Sakit] 3 | pusing=pusing2|pusing 4 | batuk=batuk 5 | deman=demam 6 | 7 | -------------------------------------------------------------------------------- /source/carik/build.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | mkdir -p lib 3 | fpc carik.lpr @extra.cfg 4 | chmod 755 ../../public_html/carik/carik.bin 5 | -------------------------------------------------------------------------------- /public_html/carik/config/.htaccess: -------------------------------------------------------------------------------- 1 | deny from all 2 | 3 | order allow,deny 4 | allow from all 5 | 6 | -------------------------------------------------------------------------------- /public_html/carik/files/.htaccess: -------------------------------------------------------------------------------- 1 | deny from all 2 | 3 | order allow,deny 4 | allow from all 5 | 6 | -------------------------------------------------------------------------------- /public_html/carik/ztemp/.htaccess: -------------------------------------------------------------------------------- 1 | deny from all 2 | 3 | order allow,deny 4 | allow from all 5 | 6 | -------------------------------------------------------------------------------- /public_html/carik/ztemp/cache/kamus/.htaccess: -------------------------------------------------------------------------------- 1 | deny from all 2 | 3 | order allow,deny 4 | allow from all 5 | 6 | -------------------------------------------------------------------------------- /public_html/carik/ztemp/cache/domains/.htaccess: -------------------------------------------------------------------------------- 1 | deny from all 2 | 3 | order allow,deny 4 | allow from all 5 | 6 | -------------------------------------------------------------------------------- /public_html/carik/ztemp/cache/jadwalsholat/.htaccess: -------------------------------------------------------------------------------- 1 | deny from all 2 | 3 | order allow,deny 4 | allow from all 5 | 6 | -------------------------------------------------------------------------------- /docker/run.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | echo Carik - Run Container 3 | echo 4 | echo 5 | 6 | docker run -it -p 8080:80 carik 7 | #docker run -it -v ~/shared-folder:/shared-folder -p 8080:80 fastplaz/$OS$RELEASE 8 | -------------------------------------------------------------------------------- /source/line/routes.pas: -------------------------------------------------------------------------------- 1 | unit routes; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | interface 6 | 7 | uses 8 | Classes, SysUtils, fastplaz_handler; 9 | 10 | implementation 11 | 12 | uses main; 13 | 14 | initialization 15 | Route.Add( 'main', TLineModule); 16 | 17 | end. 18 | 19 | -------------------------------------------------------------------------------- /source/facebook/routes.pas: -------------------------------------------------------------------------------- 1 | unit routes; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | interface 6 | 7 | uses 8 | Classes, SysUtils, fpjson, fastplaz_handler; 9 | 10 | implementation 11 | 12 | uses main; 13 | 14 | initialization 15 | Route[ '/'] := TFacebookModule; // Main Module 16 | 17 | end. 18 | 19 | -------------------------------------------------------------------------------- /public_html/carik/files/nlp/ai-questions.txt: -------------------------------------------------------------------------------- 1 | 2 | [TanyaNama] 3 | ask:Name=Bisa diinformasikan nama Anda siapa? 4 | ask:Name=Nama Anda siapa? 5 | ask:Name=Siapa nama Anda? 6 | 7 | [TanyaEmail] 8 | ask:Name=Bisa diinformasikan Email Anda apa? 9 | 10 | [TanyaNamaResponse] 11 | ask=Hi %Name%, terima kasih 12 | -------------------------------------------------------------------------------- /source/telegram/routes.pas: -------------------------------------------------------------------------------- 1 | unit routes; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | interface 6 | 7 | uses 8 | Classes, SysUtils, fpjson, fastplaz_handler; 9 | 10 | implementation 11 | 12 | uses main, command_controller; 13 | 14 | initialization 15 | Route['/command'] := TCommandController; 16 | Route['/'] := TTelegramModule; 17 | //Route['main'] := TTelegramModule; 18 | 19 | end. 20 | 21 | -------------------------------------------------------------------------------- /public_html/carik/files/nlp/dokter-intents.txt: -------------------------------------------------------------------------------- 1 | 2 | [DokterGreeting] 3 | say=@Greeting @Profesi:dokter 4 | say=@Waktu:waktu 5 | 6 | [DokterGejala] 7 | say=@Sapaan:aku @apapun @Sakit 8 | say=@Sapaan:aku @Sakit 9 | 10 | [DokterDitanya] 11 | say=@Sapaan:aku @apapun (t|n)anya @Profesi:dokter 12 | say=@Sapaan:aku @apapun (t|n)anya ke @Profesi:dokter 13 | 14 | [DokterTanya] 15 | say=obat untuk @Sakit 16 | say=obat @Sakit 17 | -------------------------------------------------------------------------------- /source/carik/routes.pas: -------------------------------------------------------------------------------- 1 | unit routes; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | interface 6 | 7 | uses 8 | Classes, SysUtils, fpjson, fastplaz_handler, loader_controller; 9 | 10 | implementation 11 | 12 | uses info_controller, main, command_controller; 13 | 14 | initialization 15 | Route[ '/command'] := TCommandController; 16 | Route[ '/loader'] := TLoaderController; 17 | Route[ '/'] := TCarikModule; // Main Module 18 | 19 | end. 20 | 21 | -------------------------------------------------------------------------------- /docker/bash.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | echo Carik - Run Container 3 | echo 4 | echo Sample Project: Carik Bot Framework 5 | echo dir: /projects/carik 6 | echo 7 | echo How to compile: 8 | echo $ cd /projects/carik/source/echo/ 9 | echo $ ./clean.sh 10 | echo $ ./compile.sh 11 | echo 12 | echo Output File: 13 | echo /projects/echo/public_htm/carik.bin 14 | echo 15 | 16 | docker run -it -p 8080:80 carik bash 17 | #docker run -it -v ~/shared-folder:/shared-folder -p 8080:80 carik bash 18 | -------------------------------------------------------------------------------- /public_html/carik/files/nlp/dokter-response.txt: -------------------------------------------------------------------------------- 1 | 2 | [DokterGreeting] 3 | say=halo, selamat %time_session% 4 | 5 | [DokterGejala] 6 | say=Coba periksa ke dokter 7 | say=Coba diobati 8 | 9 | [DokterDitanya] 10 | say=iya, tapi saya hanya BotDokter saja 11 | say=iya, tapi saya hanya BotDokter saja. Saya menyarankan Anda menghubungi langsung ke dokter 12 | say=sebaiknya Anda langsung hubungi dokter anda. 13 | 14 | [DokterTanya] 15 | say=tentunya obat %Sakit_value% 16 | say=coba ke apotek, beli obat %Sakit_value% 17 | 18 | 19 | 20 | -------------------------------------------------------------------------------- /docker/files/echo-run.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | # pull requirement files 4 | #cd /projects/vendors/fastplaz/ 5 | #git pull origin development 6 | 7 | # pull update 8 | echo Pull update from echo repository 9 | cd /projects/echo/ 10 | git pull 11 | 12 | # compile and deploy 13 | echo Compiling .... 14 | cd /projects/echo/source/echo && ./compile.sh 15 | 16 | echo 17 | echo Update and Compiling done 18 | echo 19 | echo Running Apache .. 20 | echo 21 | echo Try from your browser 22 | echo http://localhost:8080/?val1=value1 23 | echo 24 | echo Try with any parameters using GET or POST method 25 | echo 26 | echo 27 | echo press Ctrl+C to exit 28 | /usr/sbin/apache2ctl -D FOREGROUND 29 | -------------------------------------------------------------------------------- /public_html/carik/files/nlp/cs-intents.txt: -------------------------------------------------------------------------------- 1 | 2 | [R123CSUploadListing] 3 | say=@Tanya:bagaimana @apapun (upload|aplod) listing 4 | say=(upload|aplod) listing 5 | 6 | [R123CSKantorLokasi] 7 | say=dimana alamat kantor 8 | say=kantornya dimana 9 | say=kantor dimana 10 | say=kantor di mana 11 | say=alamat (dimana|di mana) 12 | say=alamat kantor 13 | say=alamat 14 | 15 | [R123CSRekening] 16 | say=nomor rekening 17 | say=norek 18 | 19 | [R123CSNoTelepon] 20 | say=(nomor|nmr|no) (telepon|telpon|telp|tlp) 21 | say=notelp 22 | 23 | 24 | [HRDGajian] 25 | object=gajian 26 | say=@Sedang:sudah gajian 27 | 28 | [HRDGajiKapan] 29 | object=gajian 30 | say=@Tanya:kapan gajian 31 | say=gajian @Tanya:kapan 32 | say=gaji @apapun @Tanya:kapan 33 | -------------------------------------------------------------------------------- /source/cli/clean.sh: -------------------------------------------------------------------------------- 1 | rm -rf .DS_Store 2 | rm -rf *.or 3 | rm -rf *.bak 4 | rm -rf *.exe 5 | rm -rf *.ppu 6 | rm -rf *.o 7 | rm -rf *.compiled 8 | 9 | find . -type f -name *.~ -delete 10 | find . -type f -name *.o -delete 11 | find . -type f -name *.oe -delete 12 | find . -type f -name *.bin -delete 13 | find . -type f -name *.rst -delete 14 | find . -type f -name *.bak -delete 15 | find . -type f -name *.ppu -delete 16 | find . -type f -name *.log -delete 17 | find . -type f -name *.ses -delete 18 | find . -type f -name *.compiled -delete 19 | find . -type f -name .DS_Store -delete 20 | find . -type d -name lib -exec rm -rf "{}" + 21 | find . -type d -name backup -exec rm -rf "{}" + 22 | 23 | mkdir lib 24 | touch lib/index.html 25 | -------------------------------------------------------------------------------- /source/carik/clean.sh: -------------------------------------------------------------------------------- 1 | rm -rf .DS_Store 2 | rm -rf *.or 3 | rm -rf *.bak 4 | rm -rf *.exe 5 | rm -rf *.ppu 6 | rm -rf *.o 7 | rm -rf *.compiled 8 | 9 | find . -type f -name *.~ -delete 10 | find . -type f -name *.o -delete 11 | find . -type f -name *.oe -delete 12 | find . -type f -name *.bin -delete 13 | find . -type f -name *.rst -delete 14 | find . -type f -name *.bak -delete 15 | find . -type f -name *.ppu -delete 16 | find . -type f -name *.log -delete 17 | find . -type f -name *.ses -delete 18 | find . -type f -name *.compiled -delete 19 | find . -type f -name .DS_Store -delete 20 | find . -type d -name lib -exec rm -rf "{}" + 21 | find . -type d -name backup -exec rm -rf "{}" + 22 | 23 | mkdir lib 24 | touch lib/index.html 25 | -------------------------------------------------------------------------------- /source/CarikBot.lpg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | -------------------------------------------------------------------------------- /docker/files/Dockerfile: -------------------------------------------------------------------------------- 1 | FROM fastplaz/ubuntu AS base 2 | 3 | # Configuration 4 | ARG GIT_REPO="https://github.com/luridarmawan/Carik.git" 5 | ARG WEB_DIR="/projects/Carik/public_html" 6 | 7 | # Make port 80 available to the world outside this container 8 | EXPOSE 80 9 | EXPOSE 443 10 | 11 | # DEPENDENCIES 12 | RUN cd /projects/vendors/ && git clone -b development https://github.com/luridarmawan/SimpleAI.git 13 | 14 | # remove old template and pull source from echo repository 15 | RUN git clone -b development $GIT_REPO 16 | #RUN chmod -R 777 $WEB_DIR/ztemp/ 17 | 18 | # setup apache web dir 19 | RUN mv /var/www/html /var/www/html-old 20 | RUN ln -s $WEB_DIR /var/www/html 21 | 22 | # Add file autu run 23 | ADD files/echo-run.sh /app/run.sh 24 | RUN chmod 755 /app/run.sh 25 | 26 | -------------------------------------------------------------------------------- /clean.sh: -------------------------------------------------------------------------------- 1 | rm -rf .DS_Store 2 | rm -rf *.or 3 | rm -rf *.bak 4 | rm -rf *.exe 5 | rm -rf *.ppu 6 | rm -rf *.o 7 | rm -rf *.compiled 8 | rm -rf lib/* 9 | 10 | find . -type f -name *.~ -delete 11 | find . -type f -name *.o -delete 12 | find . -type f -name *.oe -delete 13 | #find . -type f -name *.bin -delete 14 | find . -type f -name *.rst -delete 15 | find . -type f -name *.bak -delete 16 | find . -type f -name *.ppu -delete 17 | find . -type f -name *.log -delete 18 | find . -type f -name *.ses -delete 19 | find . -type f -name *.oga -delete 20 | find . -type f -name *.ogg -delete 21 | find . -type f -name *.mp3 -delete 22 | find . -type f -name *.compiled -delete 23 | find . -type f -name .DS_Store -delete 24 | find . -type d -name lib -exec rm -rf "{}" + 25 | find . -type d -name backup -exec rm -rf "{}" + 26 | -------------------------------------------------------------------------------- /public_html/carik/files/nlp/cs-response.txt: -------------------------------------------------------------------------------- 1 | 2 | [R123CSUploadListing] 3 | say=Anda harus login terlebih dahulu di Costomer-Dashboard,\nkemudian ikuti langkah2 di halaman tersebut.\nInformasi selangkapnya bisa anda jumpai di\nhttps://www.rumah123.com/faq 4 | 5 | [R123CSKantorLokasi] 6 | say=Menara DEA II\nJln Mega Kuningan Barat Kav. E-4 no 1 Lt. 7. Kuningan Timur, Setiabudi, Jakarta Selatan.\n\nInformasi lengkap kantor kami cantumkan di:\nhttps://www.rumah123.com/kontak-kami 7 | 8 | [R123CSRekening] 9 | say=BCA 123456789\nMandiri 2423424332534\n\nJangan lupa melakukan konfirmasi setelah melakukan transfer dana. 10 | 11 | [R123CSNoTelepon] 12 | say=Kami bisa dihubungi di (021) 576.1001 13 | 14 | 15 | 16 | [HRDGajian] 17 | say=sepertinya belum 18 | 19 | [HRDGajiKapan] 20 | say=ntar kalau sudah ditransfer 21 | -------------------------------------------------------------------------------- /source/line/clean.sh: -------------------------------------------------------------------------------- 1 | rm -rf .DS_Store 2 | rm -rf *.or 3 | rm -rf *.bak 4 | rm -rf *.exe 5 | rm -rf *.ppu 6 | rm -rf *.o 7 | rm -rf *.compiled 8 | rm -rf lib/* 9 | 10 | find . -type f -name *.~ -delete 11 | find . -type f -name *.o -delete 12 | find . -type f -name *.oe -delete 13 | #find . -type f -name *.bin -delete 14 | find . -type f -name *.rst -delete 15 | find . -type f -name *.bak -delete 16 | find . -type f -name *.ppu -delete 17 | find . -type f -name *.log -delete 18 | find . -type f -name *.ses -delete 19 | find . -type f -name *.oga -delete 20 | find . -type f -name *.ogg -delete 21 | find . -type f -name *.mp3 -delete 22 | find . -type f -name *.compiled -delete 23 | find . -type f -name .DS_Store -delete 24 | find . -type d -name lib -exec rm -rf "{}" + 25 | find . -type d -name backup -exec rm -rf "{}" + 26 | -------------------------------------------------------------------------------- /source/facebook/clean.sh: -------------------------------------------------------------------------------- 1 | rm -rf .DS_Store 2 | rm -rf *.or 3 | rm -rf *.bak 4 | rm -rf *.exe 5 | rm -rf *.ppu 6 | rm -rf *.o 7 | rm -rf *.compiled 8 | rm -rf lib/* 9 | 10 | find . -type f -name *.~ -delete 11 | find . -type f -name *.o -delete 12 | find . -type f -name *.oe -delete 13 | #find . -type f -name *.bin -delete 14 | find . -type f -name *.rst -delete 15 | find . -type f -name *.bak -delete 16 | find . -type f -name *.ppu -delete 17 | find . -type f -name *.log -delete 18 | find . -type f -name *.ses -delete 19 | find . -type f -name *.oga -delete 20 | find . -type f -name *.ogg -delete 21 | find . -type f -name *.mp3 -delete 22 | find . -type f -name *.compiled -delete 23 | find . -type f -name .DS_Store -delete 24 | find . -type d -name lib -exec rm -rf "{}" + 25 | find . -type d -name backup -exec rm -rf "{}" + 26 | -------------------------------------------------------------------------------- /source/telegram/clean.sh: -------------------------------------------------------------------------------- 1 | rm -rf .DS_Store 2 | rm -rf *.or 3 | rm -rf *.bak 4 | rm -rf *.exe 5 | rm -rf *.ppu 6 | rm -rf *.o 7 | rm -rf *.compiled 8 | rm -rf lib/* 9 | 10 | find . -type f -name *.~ -delete 11 | find . -type f -name *.o -delete 12 | find . -type f -name *.oe -delete 13 | #find . -type f -name *.bin -delete 14 | find . -type f -name *.rst -delete 15 | find . -type f -name *.bak -delete 16 | find . -type f -name *.ppu -delete 17 | find . -type f -name *.log -delete 18 | find . -type f -name *.ses -delete 19 | find . -type f -name *.oga -delete 20 | find . -type f -name *.ogg -delete 21 | find . -type f -name *.mp3 -delete 22 | find . -type f -name *.compiled -delete 23 | find . -type f -name .DS_Store -delete 24 | find . -type d -name lib -exec rm -rf "{}" + 25 | find . -type d -name backup -exec rm -rf "{}" + 26 | -------------------------------------------------------------------------------- /public_html/carik/files/blacklist-global.txt: -------------------------------------------------------------------------------- 1 | Test Luri,62878764690001 2 | Ace Hardware,6281314789856 3 | Bank Allo,62811681846110 4 | Bank BCA,62811615006998 5 | Bank BTPN,6281218976774 6 | Bank Mega,6282208223322 7 | Bank Mega Kartu Kredit,628226082262107 8 | Blibli Tiket,6281119215050 9 | Cinepolis Indonesia,6287777731078 10 | Citilink,6281110110808 11 | GoPay,6282117854246 12 | Grab for Business,6287778111794 13 | Honest,6281119191101 14 | Honest OTP,6281119959581 15 | Jenius,6281218976774 16 | KAI121,6281112111121 17 | Mega Life,6281197900111 18 | Prioritas Info,6281808800055 19 | Shopee Security,6285574670796 20 | Telkomsel,6281111111111 21 | Telkomsel Halo,628112022220 22 | Telkomsel Promo & Rewards,62811106878 23 | Telkomsel Promo & Rewards,6285179943885 24 | Tempo,6288225802626 25 | Traveloka Promo,628118943918 26 | Tri,628999800123 27 | UReport Unicef,628119004567 28 | uzmamedia,6285292222408 29 | Verify,16084476123 30 | whatsapp,? -------------------------------------------------------------------------------- /source/cli/extra.cfg: -------------------------------------------------------------------------------- 1 | -Px86_64 2 | #Language 3 | #-FrC:/lazarus-1.2.6/fpc/2.6.4/msg 4 | 5 | #SimpleAI & SimpleBOT Package 6 | -Fu../../../vendors/SimpleAI/source/package/src/ 7 | -Fu../../../vendors/SimpleAI/source/package/src/controller/ 8 | 9 | #-FUlib/$FPCTARGET/ 10 | -FUlib/ 11 | -Fu. 12 | -Fu.. 13 | -Fucontroller 14 | 15 | -Fu../../../vendors/fastplaz/FastPlaz 16 | -Fu../../../vendors/fastplaz/FastPlaz/src/helper 17 | -Fu../../../vendors/fastplaz/FastPlaz/src/systems 18 | -Fu../../../vendors/fastplaz/FastPlaz/src/library 19 | -Fu../../../vendors/fastplaz/FastPlaz/src/model 20 | -Fu../../../vendors/fastplaz/FastPlaz/src/integration 21 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/controller 22 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/model 23 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/util 24 | -Fu../../../vendors/fastplaz/FastPlaz/src/vendor/dcrypt 25 | 26 | -gl 27 | #-O3 28 | 29 | #-dLCL -dLCLwin32 30 | 31 | -dUseCThreads 32 | 33 | -Ficonfig/ 34 | 35 | #-o../../public_html/carik/carik.bin 36 | 37 | -------------------------------------------------------------------------------- /source/facebook/extra.cfg: -------------------------------------------------------------------------------- 1 | -Px86_64 2 | -v0 3 | -vw 4 | #Language 5 | #-FrC:/lazarus-1.2.6/fpc/2.6.4/msg 6 | 7 | #SimpleAI & SimpleBOT Package 8 | -Fu../../../vendors/SimpleAI/source/package/src/ 9 | -Fu../../../vendors/SimpleAI/source/package/src/controller/ 10 | 11 | #-FUlib/$FPCTARGET/ 12 | -FUlib/ 13 | -Fu. 14 | -Fucontroller 15 | 16 | -Fu../common 17 | -Fu../../../vendors/fastplaz/FastPlaz 18 | -Fu../../../vendors/fastplaz/FastPlaz/src/helper 19 | -Fu../../../vendors/fastplaz/FastPlaz/src/systems 20 | -Fu../../../vendors/fastplaz/FastPlaz/src/library 21 | -Fu../../../vendors/fastplaz/FastPlaz/src/model 22 | -Fu../../../vendors/fastplaz/FastPlaz/src/integration 23 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/controller 24 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/model 25 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/util 26 | -Fu../../../vendors/fastplaz/FastPlaz/src/vendor/dcrypt 27 | 28 | -O3 29 | 30 | #-dLCL -dLCLwin32 31 | 32 | -dUseCThreads 33 | 34 | -Ficonfig/ 35 | 36 | -o../../public_html/carik/facebook.bin 37 | -------------------------------------------------------------------------------- /source/carik/extra.cfg: -------------------------------------------------------------------------------- 1 | -Px86_64 2 | -v0 3 | -vw 4 | #Language 5 | #-FrC:/lazarus-1.2.6/fpc/2.6.4/msg 6 | 7 | #SimpleAI & SimpleBOT Package 8 | -Fu../../../vendors/SimpleAI/source/package/src/ 9 | -Fu../../../vendors/SimpleAI/source/package/src/controller/ 10 | 11 | #-FUlib/$FPCTARGET/ 12 | -FUlib/ 13 | -Fu. 14 | -Fucontroller 15 | 16 | -Fu../common 17 | -Fu../../../vendors/fastplaz/FastPlaz 18 | -Fu../../../vendors/fastplaz/FastPlaz/src/helper 19 | -Fu../../../vendors/fastplaz/FastPlaz/src/systems 20 | -Fu../../../vendors/fastplaz/FastPlaz/src/library 21 | -Fu../../../vendors/fastplaz/FastPlaz/src/model 22 | -Fu../../../vendors/fastplaz/FastPlaz/src/integration 23 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/controller 24 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/model 25 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/util 26 | -Fu../../../vendors/fastplaz/FastPlaz/src/vendor/dcrypt 27 | 28 | -gl 29 | #-O3 30 | 31 | #-dLCL -dLCLwin32 32 | 33 | -dUseCThreads 34 | 35 | -Ficonfig/ 36 | 37 | -o../../public_html/carik/carik.bin 38 | 39 | -------------------------------------------------------------------------------- /source/line/extra.cfg: -------------------------------------------------------------------------------- 1 | -Px86_64 2 | -v0 3 | -vw 4 | #Language 5 | #-FrC:/lazarus-1.2.6/fpc/2.6.4/msg 6 | 7 | #SimpleAI & SimpleBOT Package 8 | -Fu../../../vendors/SimpleAI/source/package/src/ 9 | -Fu../../../vendors/SimpleAI/source/package/src/controller/ 10 | 11 | #-FUlib/$FPCTARGET/ 12 | -FUlib/ 13 | -Fu. 14 | -Fu.. 15 | -Fucontroller 16 | 17 | -Fu../common 18 | -Fu../../../vendors/fastplaz/FastPlaz 19 | -Fu../../../vendors/fastplaz/FastPlaz/src/systems 20 | -Fu../../../vendors/fastplaz/FastPlaz/src/library 21 | -Fu../../../vendors/fastplaz/FastPlaz/src/model 22 | -Fu../../../vendors/fastplaz/FastPlaz/src/integration 23 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/controller 24 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/model 25 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/util 26 | -Fu../../../vendors/fastplaz/FastPlaz/src/vendor/dcrypt 27 | -Fu../../../vendors/fastplaz/FastPlaz/src/helper 28 | 29 | -O3 30 | 31 | #-dLCL -dLCLwin32 32 | 33 | -dUseCThreads 34 | 35 | -Ficonfig/ 36 | 37 | -o../../public_html/carik/line.bin 38 | 39 | -------------------------------------------------------------------------------- /source/facebook/facebook.lpr: -------------------------------------------------------------------------------- 1 | program facebook; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | uses 6 | {$IFNDEF Windows}cthreads,{$ENDIF} 7 | fpcgi, sysutils, fastplaz_handler, common, main, routes; 8 | 9 | {$R *.res} 10 | 11 | begin 12 | Application.Title:='Messenger'; 13 | Application.Email := string( Config.GetValue(_SYSTEM_WEBMASTER_EMAIL,UTF8Decode('webmaster@' + GetEnvironmentVariable('SERVER_NAME')))); 14 | Application.DefaultModuleName := string( Config.GetValue(_SYSTEM_MODULE_DEFAULT, 'main')); 15 | Application.ModuleVariable := string( Config.GetValue(_SYSTEM_MODULE_VARIABLE, 'mod')); 16 | Application.AllowDefaultModule := True; 17 | Application.RedirectOnErrorURL := string( Config.GetValue(_SYSTEM_ERROR_URL, '/')); 18 | Application.RedirectOnError:= Config.GetValue( _SYSTEM_ERROR_REDIRECT, false); 19 | 20 | Application.OnGetModule := @FastPlasAppandler.OnGetModule; 21 | Application.PreferModuleName := True; 22 | {$if FPC_FULlVERSION >= 30004} 23 | Application.LegacyRouting := True; 24 | {$endif} 25 | 26 | Application.Initialize; 27 | Application.Run; 28 | end. 29 | -------------------------------------------------------------------------------- /source/telegram/extra.cfg: -------------------------------------------------------------------------------- 1 | -Px86_64 2 | -v0 3 | -vw 4 | #Language 5 | #-FrC:/lazarus-1.2.6/fpc/2.6.4/msg 6 | 7 | #SimpleAI & SimpleBOT Package 8 | -Fu../../../vendors/SimpleAI/source/package/src/ 9 | -Fu../../../vendors/SimpleAI/source/package/src/controller/ 10 | 11 | #-FUlib/$FPCTARGET/ 12 | -FUlib/ 13 | -Fu. 14 | -Fucontroller 15 | 16 | -Fu../common 17 | -Fu../../../vendors/fastplaz/FastPlaz 18 | -Fu../../../vendors/fastplaz/FastPlaz/src/helper 19 | -Fu../../../vendors/fastplaz/FastPlaz/src/systems 20 | -Fu../../../vendors/fastplaz/FastPlaz/src/library 21 | -Fu../../../vendors/fastplaz/FastPlaz/src/model 22 | -Fu../../../vendors/fastplaz/FastPlaz/src/integration 23 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/controller 24 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/model 25 | -Fu../../../vendors/fastplaz/FastPlaz/src/cms/util 26 | -Fu../../../vendors/fastplaz/FastPlaz/src/vendor/dcrypt 27 | 28 | -O3 29 | 30 | #-dLCL -dLCLwin32 31 | 32 | -dUseCThreads 33 | 34 | -Ficonfig/ 35 | 36 | -o../../public_html/carik/telegram.bin 37 | #-o/home/ec2-user/public_html/carik/telegram2.bin 38 | 39 | -------------------------------------------------------------------------------- /source/telegram/telegram.lpr: -------------------------------------------------------------------------------- 1 | program telegram; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | uses 6 | {$IFNDEF Windows}cthreads,{$ENDIF} 7 | fpcgi, sysutils, fastplaz_handler, common, main, routes, telegram_handler, 8 | command_controller; 9 | 10 | {$R *.res} 11 | 12 | begin 13 | Application.Title:='Telegram'; 14 | Application.Email := string( Config.GetValue(_SYSTEM_WEBMASTER_EMAIL,UTF8Decode('webmaster@' + GetEnvironmentVariable('SERVER_NAME')))); 15 | Application.DefaultModuleName := string( Config.GetValue(_SYSTEM_MODULE_DEFAULT, 'main')); 16 | Application.ModuleVariable := string( Config.GetValue(_SYSTEM_MODULE_VARIABLE, 'mod')); 17 | Application.AllowDefaultModule := True; 18 | Application.RedirectOnErrorURL := string( Config.GetValue(_SYSTEM_ERROR_URL, '/')); 19 | Application.RedirectOnError:= Config.GetValue( _SYSTEM_ERROR_REDIRECT, false); 20 | 21 | Application.OnGetModule := @FastPlasAppandler.OnGetModule; 22 | Application.PreferModuleName := True; 23 | {$if FPC_FULlVERSION >= 30004} 24 | Application.LegacyRouting := True; 25 | {$endif} 26 | 27 | Application.Initialize; 28 | Application.Run; 29 | end. 30 | -------------------------------------------------------------------------------- /source/line/line.lpr: -------------------------------------------------------------------------------- 1 | program line; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | uses 6 | {$IFNDEF Windows} 7 | cthreads, 8 | {$ENDIF} 9 | fpcgi, sysutils, fastplaz_handler, common, main, routes, line_handler; 10 | 11 | begin 12 | Application.Title:='Carik - LINE Bot'; 13 | Application.Email := string( Config.GetValue(_SYSTEM_WEBMASTER_EMAIL,UTF8Decode('webmaster@' + GetEnvironmentVariable('SERVER_NAME')))); 14 | Application.DefaultModuleName := string( Config.GetValue(_SYSTEM_MODULE_DEFAULT, 'main')); 15 | Application.ModuleVariable := string( Config.GetValue(_SYSTEM_MODULE_VARIABLE, 'mod')); 16 | Application.AllowDefaultModule := True; 17 | Application.RedirectOnErrorURL := string( Config.GetValue(_SYSTEM_ERROR_URL, '/')); 18 | Application.RedirectOnError:= Config.GetValue( _SYSTEM_ERROR_REDIRECT, false); 19 | 20 | Application.OnGetModule := @FastPlasAppandler.OnGetModule; 21 | Application.PreferModuleName := True; 22 | //{$if (fpc_version=3) and (fpc_release>=0) and (fpc_patch>=4)} 23 | {$if FPC_FULlVERSION >= 30004} 24 | Application.LegacyRouting := True; 25 | {$endif} 26 | 27 | Application.Initialize; 28 | Application.Run; 29 | end. 30 | -------------------------------------------------------------------------------- /source/carik/carik.lpr: -------------------------------------------------------------------------------- 1 | program carik; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | uses 6 | {$IFNDEF Windows}cthreads,{$ENDIF} 7 | fpcgi, sysutils, fastplaz_handler, common, main, routes, direct_handler, 8 | loader_controller, command_controller; 9 | 10 | {$R *.res} 11 | 12 | begin 13 | Application.Title:='Carik'; 14 | Application.Email := string( Config.GetValue(_SYSTEM_WEBMASTER_EMAIL,UTF8Decode('webmaster@' + GetEnvironmentVariable('SERVER_NAME')))); 15 | Application.DefaultModuleName := string( Config.GetValue(_SYSTEM_MODULE_DEFAULT, 'main')); 16 | Application.ModuleVariable := string( Config.GetValue(_SYSTEM_MODULE_VARIABLE, 'mod')); 17 | Application.AllowDefaultModule := True; 18 | Application.RedirectOnErrorURL := string( Config.GetValue(_SYSTEM_ERROR_URL, '/')); 19 | Application.RedirectOnError:= Config.GetValue( _SYSTEM_ERROR_REDIRECT, false); 20 | 21 | Application.OnGetModule := @FastPlasAppandler.OnGetModule; 22 | Application.PreferModuleName := True; 23 | //{$if (fpc_version=3) and (fpc_release>=0) and (fpc_patch>=4)} 24 | {$if FPC_FULlVERSION >= 30004} 25 | Application.LegacyRouting := True; 26 | {$endif} 27 | 28 | Application.Initialize; 29 | Application.Run; 30 | end. 31 | 32 | -------------------------------------------------------------------------------- /public_html/carik/.htaccess: -------------------------------------------------------------------------------- 1 | # CORS Enabling 2 | Header set Access-Control-Allow-Origin "*" 3 | Header set Access-Control-Allow-Headers "*" 4 | Header set Access-Control-Allow-Methods "GET, POST, PUT, DELETE, OPTIONS" 5 | Header set X-Frame-Options SAMEORIGIN 6 | 7 | #Header set Access-Control-Allow-Origin "*" 8 | 9 | # Generated by FastPlaz 10 | 11 | RewriteEngine On 12 | AddHandler cgi-script .cgi 13 | AddHandler cgi-script .bin 14 | AddHandler cgi-script .pas 15 | AddHandler cgi-script .exe 16 | Options +ExecCGI 17 | 18 | DirectoryIndex carik.bin index.html 19 | 20 | SetEnvIf Authorization "(.*)" Authorization=$1 21 | SetEnvIf ClientID "(.*)" ClientID=$1 22 | SetEnvIf Token "(.*)" Token=$1 23 | SetEnvIf DeviceID "(.*)" DeviceID=$1 24 | 25 | SetEnvIf Authorization "(.*)" Authorization=$1 26 | 27 | RewriteRule ^(line)$ line.bin/$1 [QSA,L] 28 | RewriteRule ^(facebook)$ facebook.bin/$1 [QSA,L] 29 | RewriteRule ^(fb)$ facebook.bin/$1 [QSA,L] 30 | RewriteRule ^(telegram)$ telegram.bin/$1 [QSA,L] 31 | 32 | # 33 | RewriteCond %{REQUEST_FILENAME} -d [OR] 34 | RewriteCond %{REQUEST_FILENAME} -f [OR] 35 | RewriteCond %{REQUEST_FILENAME} -l 36 | RewriteRule ^(.*)$ - [NC,L] 37 | #RewriteRule ^(.*)$ 404.php [QSA,L] 38 | RewriteRule ^(.*)$ carik.bin/$1 [QSA,L] 39 | 40 | -------------------------------------------------------------------------------- /source/carik/main.pas: -------------------------------------------------------------------------------- 1 | unit main; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | interface 6 | 7 | uses 8 | direct_handler, 9 | Classes, SysUtils, fpcgi, fpjson, json_lib, HTTPDefs, fastplaz_handler, 10 | database_lib, string_helpers, dateutils, datetime_helpers; 11 | 12 | type 13 | 14 | { TCarikModule } 15 | 16 | TCarikModule = class(TCarikHandler) 17 | private 18 | procedure BeforeRequestHandler(Sender: TObject; ARequest: TRequest); 19 | function OnMessageHandler(AMessage: string; var Handled: boolean): string; 20 | function OnErrorHandler(AMessage: string; var Handled: boolean): string; 21 | public 22 | constructor CreateNew(AOwner: TComponent; CreateMode: integer); override; 23 | destructor Destroy; override; 24 | 25 | end; 26 | 27 | implementation 28 | 29 | uses common; 30 | 31 | constructor TCarikModule.CreateNew(AOwner: TComponent; CreateMode: integer); 32 | begin 33 | inherited CreateNew(AOwner, CreateMode); 34 | BeforeRequest := @BeforeRequestHandler; 35 | OnMessage := @OnMessageHandler; 36 | OnError := @OnErrorHandler; 37 | end; 38 | 39 | destructor TCarikModule.Destroy; 40 | begin 41 | inherited Destroy; 42 | end; 43 | 44 | // Init First 45 | procedure TCarikModule.BeforeRequestHandler(Sender: TObject; ARequest: TRequest 46 | ); 47 | begin 48 | Response.ContentType := 'application/json'; 49 | end; 50 | 51 | function TCarikModule.OnMessageHandler(AMessage: string; var Handled: boolean 52 | ): string; 53 | begin 54 | Result := ''; 55 | //Result := 'echo: ' + Carik.UserID + '/' + AMessage; 56 | //Handled := true; 57 | end; 58 | 59 | function TCarikModule.OnErrorHandler(AMessage: string; var Handled: boolean 60 | ): string; 61 | begin 62 | //Result := 'your error message: ' + AMessage; 63 | //Handled:= True; 64 | end; 65 | 66 | 67 | 68 | 69 | end. 70 | 71 | -------------------------------------------------------------------------------- /source/line/main.pas: -------------------------------------------------------------------------------- 1 | unit main; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | interface 6 | 7 | uses 8 | line_handler, 9 | Classes, SysUtils, fpcgi, fpjson, json_lib, HTTPDefs, fastplaz_handler, 10 | database_lib, string_helpers, dateutils, datetime_helpers; 11 | 12 | type 13 | 14 | { TLineModule } 15 | 16 | TLineModule = class(TLineHandler) 17 | private 18 | procedure BeforeRequestHandler(Sender: TObject; ARequest: TRequest); 19 | function OnMessageHandler(AMessage: string; var Handled: boolean): string; 20 | function OnErrorHandler(AMessage: string; var Handled: boolean): string; 21 | function OnSpamHandler(AMessage: string; Score: integer; 22 | var Handled: boolean): string; 23 | public 24 | constructor CreateNew(AOwner: TComponent; CreateMode: integer); override; 25 | destructor Destroy; override; 26 | end; 27 | 28 | implementation 29 | 30 | uses common; 31 | 32 | constructor TLineModule.CreateNew(AOwner: TComponent; CreateMode: integer); 33 | begin 34 | inherited CreateNew(AOwner, CreateMode); 35 | BeforeRequest := @BeforeRequestHandler; 36 | OnMessage := @OnMessageHandler; 37 | OnError := @OnErrorHandler; 38 | OnSpam := @OnSpamHandler; 39 | end; 40 | 41 | destructor TLineModule.Destroy; 42 | begin 43 | inherited Destroy; 44 | end; 45 | 46 | // Init First 47 | procedure TLineModule.BeforeRequestHandler(Sender: TObject; ARequest: TRequest); 48 | begin 49 | Response.ContentType := 'application/json'; 50 | end; 51 | 52 | function TLineModule.OnMessageHandler(AMessage: string; 53 | var Handled: boolean): string; 54 | begin 55 | Result := ''; 56 | //Result := 'echo: ' + Carik.UserID + '/' + AMessage; 57 | //Handled := true; 58 | end; 59 | 60 | function TLineModule.OnErrorHandler(AMessage: string; 61 | var Handled: boolean): string; 62 | begin 63 | //Result := 'your error message: ' + AMessage; 64 | //Handled:= True; 65 | end; 66 | 67 | function TLineModule.OnSpamHandler(AMessage: string; Score: integer; 68 | var Handled: boolean): string; 69 | begin 70 | 71 | end; 72 | 73 | end. 74 | 75 | 76 | 77 | -------------------------------------------------------------------------------- /source/facebook/main.pas: -------------------------------------------------------------------------------- 1 | unit main; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | interface 6 | 7 | uses 8 | facebook_handler, 9 | Classes, SysUtils, fpcgi, fpjson, json_lib, HTTPDefs, fastplaz_handler, 10 | database_lib, string_helpers, dateutils, datetime_helpers; 11 | 12 | type 13 | 14 | { TFacebookModule } 15 | 16 | TFacebookModule = class(TFacebookHandler) 17 | private 18 | procedure BeforeRequestHandler(Sender: TObject; ARequest: TRequest); 19 | function OnMessageHandler(AMessage: string; var Handled: boolean): string; 20 | function OnErrorHandler(AMessage: string; var Handled: boolean): string; 21 | function OnSpamHandler(AMessage: string; Score: integer; 22 | var Handled: boolean): string; 23 | public 24 | constructor CreateNew(AOwner: TComponent; CreateMode: integer); override; 25 | destructor Destroy; override; 26 | end; 27 | 28 | implementation 29 | 30 | uses common; 31 | 32 | constructor TFacebookModule.CreateNew(AOwner: TComponent; CreateMode: integer); 33 | begin 34 | inherited CreateNew(AOwner, CreateMode); 35 | BeforeRequest := @BeforeRequestHandler; 36 | OnMessage := @OnMessageHandler; 37 | OnError := @OnErrorHandler; 38 | OnSpam := @OnSpamHandler; 39 | end; 40 | 41 | destructor TFacebookModule.Destroy; 42 | begin 43 | inherited Destroy; 44 | end; 45 | 46 | // Init First 47 | procedure TFacebookModule.BeforeRequestHandler(Sender: TObject; ARequest: TRequest); 48 | begin 49 | Response.ContentType := 'application/json'; 50 | end; 51 | 52 | function TFacebookModule.OnMessageHandler(AMessage: string; 53 | var Handled: boolean): string; 54 | begin 55 | Result := ''; 56 | //Result := 'echo: ' + Carik.UserID + '/' + AMessage; 57 | //Handled := true; 58 | end; 59 | 60 | function TFacebookModule.OnErrorHandler(AMessage: string; 61 | var Handled: boolean): string; 62 | begin 63 | //Result := 'your error message: ' + AMessage; 64 | //Handled:= True; 65 | end; 66 | 67 | function TFacebookModule.OnSpamHandler(AMessage: string; Score: integer; 68 | var Handled: boolean): string; 69 | begin 70 | 71 | end; 72 | 73 | end. 74 | 75 | 76 | 77 | -------------------------------------------------------------------------------- /source/cli/carik.lpi: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | <UseAppBundle Value="False"/> 14 | <ResourceType Value="res"/> 15 | </General> 16 | <i18n> 17 | <EnableI18N LFM="False"/> 18 | </i18n> 19 | <BuildModes Count="1"> 20 | <Item1 Name="Default" Default="True"/> 21 | </BuildModes> 22 | <PublishOptions> 23 | <Version Value="2"/> 24 | </PublishOptions> 25 | <RunParams> 26 | <FormatVersion Value="2"/> 27 | <Modes Count="1"> 28 | <Mode0 Name="default"/> 29 | </Modes> 30 | </RunParams> 31 | <RequiredPackages Count="2"> 32 | <Item1> 33 | <PackageName Value="simplebot_package"/> 34 | </Item1> 35 | <Item2> 36 | <PackageName Value="fastplaz_runtime"/> 37 | </Item2> 38 | </RequiredPackages> 39 | <Units Count="2"> 40 | <Unit0> 41 | <Filename Value="carik.lpr"/> 42 | <IsPartOfProject Value="True"/> 43 | </Unit0> 44 | <Unit1> 45 | <Filename Value="..\carik_webmodule.pas"/> 46 | <IsPartOfProject Value="True"/> 47 | </Unit1> 48 | </Units> 49 | </ProjectOptions> 50 | <CompilerOptions> 51 | <Version Value="11"/> 52 | <PathDelim Value="\"/> 53 | <Target> 54 | <Filename Value=".\carik"/> 55 | </Target> 56 | <SearchPaths> 57 | <IncludeFiles Value="$(ProjOutDir)"/> 58 | <OtherUnitFiles Value=".."/> 59 | <UnitOutputDirectory Value="lib\$(TargetCPU)-$(TargetOS)"/> 60 | </SearchPaths> 61 | </CompilerOptions> 62 | <Debugging> 63 | <Exceptions Count="3"> 64 | <Item1> 65 | <Name Value="EAbort"/> 66 | </Item1> 67 | <Item2> 68 | <Name Value="ECodetoolError"/> 69 | </Item2> 70 | <Item3> 71 | <Name Value="EFOpenError"/> 72 | </Item3> 73 | </Exceptions> 74 | </Debugging> 75 | </CONFIG> 76 | -------------------------------------------------------------------------------- /source/facebook/facebook.lpi: -------------------------------------------------------------------------------- 1 | <?xml version="1.0" encoding="UTF-8"?> 2 | <CONFIG> 3 | <ProjectOptions> 4 | <Version Value="12"/> 5 | <General> 6 | <Flags> 7 | <MainUnitHasCreateFormStatements Value="False"/> 8 | <CompatibilityMode Value="True"/> 9 | </Flags> 10 | <SessionStorage Value="InProjectDir"/> 11 | <Title Value="Messaging"/> 12 | <UseAppBundle Value="False"/> 13 | <ResourceType Value="res"/> 14 | </General> 15 | <VersionInfo> 16 | <UseVersionInfo Value="True"/> 17 | <AutoIncrementBuild Value="True"/> 18 | <MinorVersionNr Value="12"/> 19 | <RevisionNr Value="15"/> 20 | <BuildNr Value="2"/> 21 | </VersionInfo> 22 | <BuildModes Count="1"> 23 | <Item1 Name="Default" Default="True"/> 24 | </BuildModes> 25 | <PublishOptions> 26 | <Version Value="2"/> 27 | <UseFileFilters Value="True"/> 28 | </PublishOptions> 29 | <RunParams> 30 | <FormatVersion Value="2"/> 31 | </RunParams> 32 | <RequiredPackages Count="2"> 33 | <Item1> 34 | <PackageName Value="simplebot_package"/> 35 | </Item1> 36 | <Item2> 37 | <PackageName Value="fastplaz_runtime"/> 38 | </Item2> 39 | </RequiredPackages> 40 | <Units Count="5"> 41 | <Unit0> 42 | <Filename Value="facebook.lpr"/> 43 | <IsPartOfProject Value="True"/> 44 | </Unit0> 45 | <Unit1> 46 | <Filename Value="routes.pas"/> 47 | <IsPartOfProject Value="True"/> 48 | </Unit1> 49 | <Unit2> 50 | <Filename Value="main.pas"/> 51 | <IsPartOfProject Value="True"/> 52 | </Unit2> 53 | <Unit3> 54 | <Filename Value="../common/carik_webmodule.pas"/> 55 | <IsPartOfProject Value="True"/> 56 | </Unit3> 57 | <Unit4> 58 | <Filename Value="../common/facebook_handler.pas"/> 59 | <IsPartOfProject Value="True"/> 60 | </Unit4> 61 | </Units> 62 | </ProjectOptions> 63 | <CompilerOptions> 64 | <Version Value="11"/> 65 | <Target> 66 | <Filename Value="../../public_html/carik/facebook.bin" ApplyConventions="False"/> 67 | </Target> 68 | <SearchPaths> 69 | <IncludeFiles Value="$(ProjOutDir)"/> 70 | <OtherUnitFiles Value="../common"/> 71 | <UnitOutputDirectory Value="lib/$(TargetCPU)-$(TargetOS)"/> 72 | </SearchPaths> 73 | <Other> 74 | <ConfigFile> 75 | <ConfigFilePath Value="extra.cfg"/> 76 | </ConfigFile> 77 | </Other> 78 | </CompilerOptions> 79 | </CONFIG> 80 | -------------------------------------------------------------------------------- /source/telegram/main.pas: -------------------------------------------------------------------------------- 1 | unit main; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | interface 6 | 7 | uses 8 | telegram_handler, 9 | Classes, SysUtils, fpcgi, fpjson, HTTPDefs, fastplaz_handler, 10 | dateutils, string_helpers, datetime_helpers; 11 | 12 | type 13 | 14 | { TTelegramModule } 15 | 16 | TTelegramModule = class(TTelegramHandler) 17 | private 18 | procedure BeforeRequestHandler(Sender: TObject; ARequest: TRequest); 19 | function OnMessageHandler(AMessage: string; var Handled: boolean): string; 20 | function OnErrorHandler(AMessage: string; var Handled: boolean): string; 21 | function OnSpamHandler(AMessage: string; Score: integer; var Handled: boolean): string; 22 | public 23 | constructor CreateNew(AOwner: TComponent; CreateMode: integer); override; 24 | destructor Destroy; override; 25 | end; 26 | 27 | implementation 28 | 29 | uses common; 30 | 31 | constructor TTelegramModule.CreateNew(AOwner: TComponent; CreateMode: integer); 32 | begin 33 | inherited CreateNew(AOwner, CreateMode); 34 | BeforeRequest := @BeforeRequestHandler; 35 | OnMessage := @OnMessageHandler; 36 | OnError := @OnErrorHandler; 37 | OnSpam := @OnSpamHandler; 38 | end; 39 | 40 | destructor TTelegramModule.Destroy; 41 | begin 42 | inherited Destroy; 43 | end; 44 | 45 | // Init First 46 | procedure TTelegramModule.BeforeRequestHandler(Sender: TObject; ARequest: TRequest); 47 | begin 48 | Response.ContentType := 'application/json'; 49 | end; 50 | 51 | function TTelegramModule.OnMessageHandler(AMessage: string; 52 | var Handled: boolean): string; 53 | begin 54 | //Result := 'echo: ' + Carik.UserID + '/' + AMessage; 55 | //Handled := true; 56 | 57 | Result := ''; 58 | end; 59 | 60 | function TTelegramModule.OnErrorHandler(AMessage: string; var Handled: boolean): string; 61 | begin 62 | //Result := 'your error message: ' + AMessage; 63 | //Handled:= True; 64 | 65 | Result := ''; 66 | end; 67 | 68 | function TTelegramModule.OnSpamHandler(AMessage: string; Score: integer; 69 | var Handled: boolean): string; 70 | var 71 | suffixMessage: string; 72 | begin 73 | suffixMessage := TELEGRAM.GroupAdminList(TELEGRAM.ChatID); 74 | //suffixMessage := '\n@' + suffixMessage.Replace(',', ', @'); 75 | 76 | Result := 'Pesan ini terdeteksi sebagai spamming, abaikan jika bukan.'; 77 | if TELEGRAM.AdminListAsJson.Count > 0 then 78 | begin 79 | Result := Result + '\nSaya colek admin: ' + suffixMessage; 80 | end 81 | else 82 | begin 83 | Result := Result + '\nSaya tidak menemukan ada admin di sini.'; 84 | end; 85 | Result := Result + '\n_('+Score.ToString+')_'; 86 | Handled:= True; 87 | end; 88 | 89 | end. 90 | 91 | 92 | 93 | 94 | 95 | -------------------------------------------------------------------------------- /source/telegram/telegram.lpi: -------------------------------------------------------------------------------- 1 | <?xml version="1.0" encoding="UTF-8"?> 2 | <CONFIG> 3 | <ProjectOptions> 4 | <Version Value="12"/> 5 | <General> 6 | <Flags> 7 | <MainUnitHasCreateFormStatements Value="False"/> 8 | <CompatibilityMode Value="True"/> 9 | </Flags> 10 | <SessionStorage Value="InProjectDir"/> 11 | <Title Value="Telegram"/> 12 | <UseAppBundle Value="False"/> 13 | <ResourceType Value="res"/> 14 | </General> 15 | <VersionInfo> 16 | <UseVersionInfo Value="True"/> 17 | <AutoIncrementBuild Value="True"/> 18 | <MinorVersionNr Value="12"/> 19 | <RevisionNr Value="15"/> 20 | <BuildNr Value="3"/> 21 | <StringTable CompanyName="Carik" OriginalFilename="telegram.bin"/> 22 | </VersionInfo> 23 | <BuildModes Count="1"> 24 | <Item1 Name="Default" Default="True"/> 25 | </BuildModes> 26 | <PublishOptions> 27 | <Version Value="2"/> 28 | <UseFileFilters Value="True"/> 29 | </PublishOptions> 30 | <RunParams> 31 | <FormatVersion Value="2"/> 32 | </RunParams> 33 | <RequiredPackages Count="2"> 34 | <Item1> 35 | <PackageName Value="simplebot_package"/> 36 | </Item1> 37 | <Item2> 38 | <PackageName Value="fastplaz_runtime"/> 39 | </Item2> 40 | </RequiredPackages> 41 | <Units Count="6"> 42 | <Unit0> 43 | <Filename Value="telegram.lpr"/> 44 | <IsPartOfProject Value="True"/> 45 | </Unit0> 46 | <Unit1> 47 | <Filename Value="routes.pas"/> 48 | <IsPartOfProject Value="True"/> 49 | </Unit1> 50 | <Unit2> 51 | <Filename Value="main.pas"/> 52 | <IsPartOfProject Value="True"/> 53 | </Unit2> 54 | <Unit3> 55 | <Filename Value="../common/telegram_handler.pas"/> 56 | <IsPartOfProject Value="True"/> 57 | </Unit3> 58 | <Unit4> 59 | <Filename Value="../common/carik_webmodule.pas"/> 60 | <IsPartOfProject Value="True"/> 61 | </Unit4> 62 | <Unit5> 63 | <Filename Value="../common/command_controller.pas"/> 64 | <IsPartOfProject Value="True"/> 65 | </Unit5> 66 | </Units> 67 | </ProjectOptions> 68 | <CompilerOptions> 69 | <Version Value="11"/> 70 | <Target> 71 | <Filename Value="../../public_html/carik/telegram.bin" ApplyConventions="False"/> 72 | </Target> 73 | <SearchPaths> 74 | <IncludeFiles Value="$(ProjOutDir)"/> 75 | <OtherUnitFiles Value="../common"/> 76 | <UnitOutputDirectory Value="lib/$(TargetCPU)-$(TargetOS)"/> 77 | </SearchPaths> 78 | <Other> 79 | <Verbosity> 80 | <ShowNotes Value="False"/> 81 | </Verbosity> 82 | <ConfigFile> 83 | <ConfigFilePath Value="extra.cfg"/> 84 | </ConfigFile> 85 | </Other> 86 | </CompilerOptions> 87 | </CONFIG> 88 | -------------------------------------------------------------------------------- /source/line/line.lpi: -------------------------------------------------------------------------------- 1 | <?xml version="1.0" encoding="UTF-8"?> 2 | <CONFIG> 3 | <ProjectOptions> 4 | <Version Value="12"/> 5 | <General> 6 | <Flags> 7 | <MainUnitHasCreateFormStatements Value="False"/> 8 | <CompatibilityMode Value="True"/> 9 | </Flags> 10 | <SessionStorage Value="InProjectDir"/> 11 | <Title Value="Line"/> 12 | <UseAppBundle Value="False"/> 13 | <ResourceType Value="res"/> 14 | </General> 15 | <i18n> 16 | <EnableI18N LFM="False"/> 17 | </i18n> 18 | <BuildModes Count="1"> 19 | <Item1 Name="Default" Default="True"/> 20 | </BuildModes> 21 | <PublishOptions> 22 | <Version Value="2"/> 23 | </PublishOptions> 24 | <RunParams> 25 | <FormatVersion Value="2"/> 26 | <Modes Count="1"> 27 | <Mode0 Name="default"/> 28 | </Modes> 29 | </RunParams> 30 | <RequiredPackages Count="4"> 31 | <Item1> 32 | <PackageName Value="simplebot_package"/> 33 | </Item1> 34 | <Item2> 35 | <PackageName Value="fastplaz_integration"/> 36 | </Item2> 37 | <Item3> 38 | <PackageName Value="LCL"/> 39 | </Item3> 40 | <Item4> 41 | <PackageName Value="fastplaz_runtime"/> 42 | </Item4> 43 | </RequiredPackages> 44 | <Units Count="5"> 45 | <Unit0> 46 | <Filename Value="line.lpr"/> 47 | <IsPartOfProject Value="True"/> 48 | </Unit0> 49 | <Unit1> 50 | <Filename Value="routes.pas"/> 51 | <IsPartOfProject Value="True"/> 52 | </Unit1> 53 | <Unit2> 54 | <Filename Value="main.pas"/> 55 | <IsPartOfProject Value="True"/> 56 | </Unit2> 57 | <Unit3> 58 | <Filename Value="../common/carik_webmodule.pas"/> 59 | <IsPartOfProject Value="True"/> 60 | </Unit3> 61 | <Unit4> 62 | <Filename Value="../common/line_handler.pas"/> 63 | <IsPartOfProject Value="True"/> 64 | </Unit4> 65 | </Units> 66 | </ProjectOptions> 67 | <CompilerOptions> 68 | <Version Value="11"/> 69 | <Target> 70 | <Filename Value="../../public_html/carik/line.bin" ApplyConventions="False"/> 71 | </Target> 72 | <SearchPaths> 73 | <IncludeFiles Value="$(ProjOutDir)"/> 74 | <OtherUnitFiles Value="..;../common"/> 75 | <UnitOutputDirectory Value="lib/$(TargetCPU)-$(TargetOS)"/> 76 | </SearchPaths> 77 | <Other> 78 | <ConfigFile> 79 | <ConfigFilePath Value="extra.cfg"/> 80 | </ConfigFile> 81 | </Other> 82 | </CompilerOptions> 83 | <Debugging> 84 | <Exceptions Count="3"> 85 | <Item1> 86 | <Name Value="EAbort"/> 87 | </Item1> 88 | <Item2> 89 | <Name Value="ECodetoolError"/> 90 | </Item2> 91 | <Item3> 92 | <Name Value="EFOpenError"/> 93 | </Item3> 94 | </Exceptions> 95 | </Debugging> 96 | </CONFIG> 97 | -------------------------------------------------------------------------------- /source/carik/carik.lpi: -------------------------------------------------------------------------------- 1 | <?xml version="1.0" encoding="UTF-8"?> 2 | <CONFIG> 3 | <ProjectOptions> 4 | <Version Value="12"/> 5 | <General> 6 | <Flags> 7 | <MainUnitHasCreateFormStatements Value="False"/> 8 | <MainUnitHasTitleStatement Value="False"/> 9 | <MainUnitHasScaledStatement Value="False"/> 10 | <CompatibilityMode Value="True"/> 11 | </Flags> 12 | <SessionStorage Value="InProjectDir"/> 13 | <Title Value="Carik"/> 14 | <UseAppBundle Value="False"/> 15 | <ResourceType Value="res"/> 16 | </General> 17 | <VersionInfo> 18 | <UseVersionInfo Value="True"/> 19 | <AutoIncrementBuild Value="True"/> 20 | <MinorVersionNr Value="12"/> 21 | <RevisionNr Value="15"/> 22 | <BuildNr Value="5"/> 23 | </VersionInfo> 24 | <BuildModes Count="1"> 25 | <Item1 Name="Default" Default="True"/> 26 | </BuildModes> 27 | <PublishOptions> 28 | <Version Value="2"/> 29 | <UseFileFilters Value="True"/> 30 | </PublishOptions> 31 | <RunParams> 32 | <FormatVersion Value="2"/> 33 | </RunParams> 34 | <RequiredPackages Count="4"> 35 | <Item1> 36 | <PackageName Value="fastplaz_integration"/> 37 | </Item1> 38 | <Item2> 39 | <PackageName Value="simplebot_package"/> 40 | </Item2> 41 | <Item3> 42 | <PackageName Value="simpleai_package"/> 43 | </Item3> 44 | <Item4> 45 | <PackageName Value="fastplaz_runtime"/> 46 | </Item4> 47 | </RequiredPackages> 48 | <Units Count="7"> 49 | <Unit0> 50 | <Filename Value="carik.lpr"/> 51 | <IsPartOfProject Value="True"/> 52 | </Unit0> 53 | <Unit1> 54 | <Filename Value="routes.pas"/> 55 | <IsPartOfProject Value="True"/> 56 | </Unit1> 57 | <Unit2> 58 | <Filename Value="main.pas"/> 59 | <IsPartOfProject Value="True"/> 60 | </Unit2> 61 | <Unit3> 62 | <Filename Value="../common/direct_handler.pas"/> 63 | <IsPartOfProject Value="True"/> 64 | </Unit3> 65 | <Unit4> 66 | <Filename Value="../common/carik_webmodule.pas"/> 67 | <IsPartOfProject Value="True"/> 68 | </Unit4> 69 | <Unit5> 70 | <Filename Value="../common/loader_controller.pas"/> 71 | <IsPartOfProject Value="True"/> 72 | </Unit5> 73 | <Unit6> 74 | <Filename Value="../common/command_controller.pas"/> 75 | <IsPartOfProject Value="True"/> 76 | </Unit6> 77 | </Units> 78 | </ProjectOptions> 79 | <CompilerOptions> 80 | <Version Value="11"/> 81 | <Target> 82 | <Filename Value="../../public_html/carik/carik.bin" ApplyConventions="False"/> 83 | </Target> 84 | <SearchPaths> 85 | <IncludeFiles Value="$(ProjOutDir)"/> 86 | <OtherUnitFiles Value="../common"/> 87 | <UnitOutputDirectory Value="lib/$(TargetCPU)-$(TargetOS)"/> 88 | </SearchPaths> 89 | <Linking> 90 | <Debugging> 91 | <UseHeaptrc Value="True"/> 92 | </Debugging> 93 | </Linking> 94 | <Other> 95 | <ConfigFile> 96 | <ConfigFilePath Value="extra.cfg"/> 97 | </ConfigFile> 98 | </Other> 99 | </CompilerOptions> 100 | </CONFIG> 101 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | @@ -0,0 +1,164 @@ 2 | +################# 3 | +## Eclipse 4 | +################# 5 | + 6 | +*.pydevproject 7 | +.project 8 | +.metadata 9 | +bin/ 10 | +tmp/ 11 | +*.tmp 12 | +*.bak 13 | +*.swp 14 | +*~.nib 15 | +local.properties 16 | +.classpath 17 | +.settings/ 18 | +.loadpath 19 | + 20 | +# External tool builders 21 | +.externalToolBuilders/ 22 | + 23 | +# Locally stored "Eclipse launch configurations" 24 | +*.launch 25 | + 26 | +# CDT-specific 27 | +.cproject 28 | + 29 | +# PDT-specific 30 | +.buildpath 31 | + 32 | + 33 | +################# 34 | +## Visual Studio 35 | +################# 36 | + 37 | +## Ignore Visual Studio temporary files, build results, and 38 | +## files generated by popular Visual Studio add-ons. 39 | + 40 | +# User-specific files 41 | +*.suo 42 | +*.user 43 | +*.sln.docstates 44 | + 45 | +# Build results 46 | +[Dd]ebug/ 47 | +[Rr]elease/ 48 | +*_i.c 49 | +*_p.c 50 | +*.ilk 51 | +*.meta 52 | +*.obj 53 | +*.pch 54 | +*.pdb 55 | +*.pgc 56 | +*.pgd 57 | +*.rsp 58 | +*.sbr 59 | +*.tlb 60 | +*.tli 61 | +*.tlh 62 | +*.tmp 63 | +*.vspscc 64 | +.builds 65 | +*.dotCover 66 | + 67 | +## TODO: If you have NuGet Package Restore enabled, uncomment this 68 | +#packages/ 69 | + 70 | +# Visual C++ cache files 71 | +ipch/ 72 | +*.aps 73 | +*.ncb 74 | +*.opensdf 75 | +*.sdf 76 | + 77 | +# Visual Studio profiler 78 | +*.psess 79 | +*.vsp 80 | + 81 | +# ReSharper is a .NET coding add-in 82 | +_ReSharper* 83 | + 84 | +# Installshield output folder 85 | +[Ee]xpress 86 | + 87 | +# DocProject is a documentation generator add-in 88 | +DocProject/buildhelp/ 89 | +DocProject/Help/*.HxT 90 | +DocProject/Help/*.HxC 91 | +DocProject/Help/*.hhc 92 | +DocProject/Help/*.hhk 93 | +DocProject/Help/*.hhp 94 | +DocProject/Help/Html2 95 | +DocProject/Help/html 96 | + 97 | +# Click-Once directory 98 | +publish 99 | + 100 | +# Others 101 | +[Bb]in 102 | +[Oo]bj 103 | +sql 104 | +TestResults 105 | +*.Cache 106 | +ClientBin 107 | +stylecop.* 108 | +~$* 109 | +*.dbmdl 110 | +Generated_Code #added for RIA/Silverlight projects 111 | + 112 | +# Backup & report files from converting an old project file to a newer 113 | +# Visual Studio version. Backup files are not needed, because we have git ;-) 114 | +_UpgradeReport_Files/ 115 | +Backup*/ 116 | +UpgradeLog*.XML 117 | + 118 | + 119 | + 120 | +############ 121 | +## Windows 122 | +############ 123 | + 124 | +# Windows image file caches 125 | +Thumbs.db 126 | + 127 | +# Folder config file 128 | +Desktop.ini 129 | + 130 | + 131 | +############# 132 | +## Python 133 | +############# 134 | + 135 | +*.py[co] 136 | + 137 | +# Packages 138 | +*.egg 139 | +*.egg-info 140 | +dist 141 | +build 142 | +eggs 143 | +parts 144 | +bin 145 | +var 146 | +sdist 147 | +develop-eggs 148 | +.installed.cfg 149 | + 150 | +# Installer logs 151 | +pip-log.txt 152 | + 153 | +# Unit test / coverage reports 154 | +.coverage 155 | +.tox 156 | + 157 | +#Translations 158 | +*.mo 159 | + 160 | +#Mr Developer 161 | +.mr.developer.cfg 162 | + 163 | +# Mac crap 164 | +.DS_Store 165 | + 166 | # Numerous always-ignore extensions 167 | *.diff 168 | *.err 169 | *.orig 170 | *.log 171 | *.rej 172 | *.swo 173 | *.swp 174 | *.zip 175 | *.vi 176 | *~ 177 | *.sass-cache 178 | 179 | # OS or Editor folders 180 | .DS_Store 181 | ._* 182 | Thumbs.db 183 | .cache 184 | .project 185 | .settings 186 | .tmproj 187 | *.esproj 188 | nbproject 189 | *.sublime-project 190 | *.sublime-workspace 191 | 192 | # Komodo 193 | *.komodoproject 194 | .komodotools 195 | 196 | # Folders to ignore 197 | .hg 198 | .svn 199 | .CVS 200 | .idea 201 | node_modules 202 | #dist 203 | 204 | # lazarus 205 | *.compiled 206 | *.lps 207 | *.bak 208 | *.ppu 209 | *.o 210 | 211 | backup/ 212 | public_html/carik/ztemp/cache/* 213 | public_html/carik/ztemp/error_log/* 214 | public_html/carik/ztemp/sessions/* 215 | source/telegram/lib/ 216 | source/facebook/lib/ 217 | source/carik/lib/ 218 | source/line/lib/ 219 | 220 | *.dll 221 | *.exe 222 | *.bin 223 | backup.bat 224 | backup.sh 225 | -------------------------------------------------------------------------------- /source/common/loader_controller.pas: -------------------------------------------------------------------------------- 1 | unit loader_controller; 2 | { 3 | USAGE: 4 | curl http://local-bot.carik.test/ai/carik.bin/loader -X PUT 5 | } 6 | 7 | {$mode objfpc}{$H+} 8 | 9 | interface 10 | 11 | uses 12 | process, 13 | redis_controller, simplebot_controller, 14 | Classes, SysUtils, fpcgi, fpjson, json_lib, HTTPDefs, fastplaz_handler, 15 | database_lib, string_helpers, dateutils, datetime_helpers, json_helpers; 16 | 17 | {$include carik.inc} 18 | 19 | type 20 | 21 | { TLoaderController } 22 | 23 | TLoaderController = class(TMyCustomController) 24 | private 25 | FBotName, FToken: string; 26 | FRedis: TRedisConstroller; 27 | SimpleBOT: TSimpleBotModule; 28 | function loadToRedis(AKeyName: string; AFileName: string): string; 29 | public 30 | constructor CreateNew(AOwner: TComponent; CreateMode: integer); override; 31 | destructor Destroy; override; 32 | 33 | procedure Get; override; 34 | procedure Put; override; 35 | procedure Post; override; 36 | procedure Options; override; 37 | end; 38 | 39 | implementation 40 | 41 | uses common; 42 | 43 | function TLoaderController.loadToRedis(AKeyName: string; AFileName: string 44 | ): string; 45 | var 46 | s, loaderFileName: string; 47 | begin 48 | Result := 'failed'; 49 | loaderFileName := Config['redis/loader_path']; 50 | if not FileExists(loaderFileName) then 51 | begin 52 | Result := 'Loader not found'; 53 | Exit; 54 | end; 55 | 56 | if Exec('sh', [ 57 | loaderFileName, 58 | AKeyName, 59 | AFileName], s, swoNone) then 60 | begin 61 | Result := s; 62 | end; 63 | 64 | end; 65 | 66 | constructor TLoaderController.CreateNew(AOwner: TComponent; CreateMode: integer); 67 | begin 68 | inherited CreateNew(AOwner, CreateMode); 69 | FRedis := TRedisConstroller.Create(); 70 | end; 71 | 72 | destructor TLoaderController.Destroy; 73 | begin 74 | FRedis.Free; 75 | inherited Destroy; 76 | end; 77 | 78 | // GET Method Handler 79 | procedure TLoaderController.Get; 80 | begin 81 | OutputJson(0, 'Invalid Method'); 82 | end; 83 | 84 | procedure TLoaderController.Put; 85 | var 86 | s, tempFileName: string; 87 | lst: TStrings; 88 | json, outputJson: TJSONUtil; 89 | begin 90 | Response.Content := ''; 91 | 92 | //TODO: check authentication 93 | 94 | tempFileName := GetTempDir + DirectorySeparator + 'file.nlp'; 95 | tempFileName := tempFileName.Replace('//', '/'); 96 | if FileExists( tempFileName) then 97 | DeleteFile(tempFileName); 98 | 99 | FBotName := _GET['name']; 100 | FToken := _GET['token']; 101 | if FBotName.IsEmpty then 102 | FBotName := Config[CONFIG_BOTNAME]; 103 | 104 | SimpleBOT := TSimpleBotModule.Create; 105 | SimpleBOT.BotName := FBotName; 106 | SimpleBOT.LoadNLPDataFromFile; 107 | 108 | lst := TStringList.Create; 109 | json := TJSONUtil.Create; 110 | outputJson := TJSONUtil.Create; 111 | 112 | // entities 113 | SimpleBOT.SimpleAI.SimpleAILib.Intent.Entities.Data.GetStrings(lst); 114 | json.Clear; 115 | json['date'] := Now.AsString; 116 | json['data'] := base64_encode(lst.Text.Trim); 117 | json.SaveToFile(tempFileName); 118 | s := loadToRedis( FBotName + _NLP_REDIS_ENTITIES, tempFileName); 119 | outputJson['responses/entities'] := s; 120 | 121 | // intent 122 | SimpleBOT.SimpleAI.SimpleAILib.Intent.Data.GetStrings(lst); 123 | json.Clear; 124 | json['date'] := Now.AsString; 125 | json['data'] := base64_encode(lst.Text.Trim); 126 | json.SaveToFile(tempFileName); 127 | s := loadToRedis( FBotName + _NLP_REDIS_INTENTS, tempFileName); 128 | outputJson['responses/intents'] := s; 129 | 130 | // response 131 | SimpleBOT.SimpleAI.ResponseData.GetStrings(lst); 132 | json.Clear; 133 | json['date'] := Now.AsString; 134 | json['data'] := base64_encode(lst.Text.Trim); 135 | json.SaveToFile(tempFileName); 136 | s := loadToRedis( FBotName + _NLP_REDIS_RESPONSES, tempFileName); 137 | outputJson['responses/responses'] := s; 138 | 139 | Response.Content := outputJson.AsJSONFormated; 140 | outputJson.Free; 141 | json.Free; 142 | lst.Free; 143 | end; 144 | 145 | // POST Method Handler 146 | procedure TLoaderController.Post; 147 | begin 148 | Response.Content := ''; 149 | end; 150 | 151 | // OPTIONS Method Handler 152 | procedure TLoaderController.Options; 153 | begin 154 | Response.Code := 204; 155 | Response.Content := ''; 156 | end; 157 | 158 | end. 159 | 160 | 161 | -------------------------------------------------------------------------------- /source/cli/carik.lpr: -------------------------------------------------------------------------------- 1 | program carik; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | uses 6 | {$IFNDEF Windows} 7 | cthreads, 8 | {$ENDIF} 9 | fpjson, 10 | common, 11 | carik_webmodule, simplebot_controller, 12 | Classes, 13 | SysUtils, 14 | CustApp, 15 | fastplaz_handler, 16 | config_lib; 17 | 18 | type 19 | 20 | { TCarik } 21 | 22 | TCarik = class(TCustomApplication) 23 | private 24 | SimpleBOT: TSimpleBotModule; 25 | 26 | function getText: string; 27 | function RemoveMarkDown(AText: string): string; 28 | function OnErrorHandler(const Message: string): string; 29 | protected 30 | procedure DoRun; override; 31 | public 32 | constructor Create(TheOwner: TComponent); override; 33 | destructor Destroy; override; 34 | procedure WriteHelp; virtual; 35 | end; 36 | 37 | { TCarik } 38 | 39 | function TCarik.getText: string; 40 | var 41 | i: integer; 42 | begin 43 | Result := ''; 44 | if ParamCount = 0 then 45 | Exit; 46 | 47 | for i := 1 to ParamCount do 48 | begin 49 | Result := Result + ' ' + Params[i]; 50 | end; 51 | end; 52 | 53 | function TCarik.RemoveMarkDown(AText: string): string; 54 | begin 55 | Result := preg_replace('\*\*(.*?)\*\*', '*$1*', AText); // bold 56 | Result := preg_replace('_(.*?)_', '$1', Result); // italic 57 | Result := preg_replace('\[(.+)\]\((.+)\)', '$2', Result); // url 58 | Result := preg_replace('tel:(.*?)', '$1', Result); // link tel:123456 59 | Result := preg_replace('```(.*?)```', '\n$1\n', Result); // skrip 60 | Result := Trim(Result); 61 | end; 62 | 63 | function TCarik.OnErrorHandler(const Message: string): string; 64 | begin 65 | Result := 'error nihh...'; samain dgn onerror carik_webmodule 66 | end; 67 | 68 | procedure TCarik.DoRun; 69 | var 70 | i: integer; 71 | text, 72 | ErrorMsg: string; 73 | json, j2: TJSONData; 74 | begin 75 | // quick check parameters 76 | ErrorMsg := CheckOptions('h', 'help'); 77 | if ErrorMsg <> '' then 78 | begin 79 | ShowException(Exception.Create(ErrorMsg)); 80 | Terminate; 81 | Exit; 82 | end; 83 | 84 | // parse parameters 85 | if HasOption('h', 'help') then 86 | begin 87 | WriteHelp; 88 | Terminate; 89 | Exit; 90 | end; 91 | 92 | { add your program here } 93 | 94 | SimpleBOT.SimpleAI.AdditionalParameters.Values['OriginalText'] := getText; 95 | SimpleBOT.CLI := True; 96 | text := SimpleBOT.Exec(getText); 97 | if not text.IsEmpty then 98 | begin 99 | json := GetJSON(text); 100 | try 101 | text := json.GetPath('response.text').AsJSON; 102 | j2 := GetJSON(text); 103 | text := ''; 104 | for i:=0 to j2.Count-1 do 105 | begin 106 | text := text + #13 + j2.Items[i].AsString; 107 | end; 108 | except 109 | text := ''; 110 | end; 111 | end; 112 | text := RemoveMarkDown(text); 113 | text := text.Replace('\n', #10); 114 | text := trim(text); 115 | WriteLn(text); 116 | 117 | // stop program loop 118 | json.Free; 119 | Terminate; 120 | end; 121 | 122 | constructor TCarik.Create(TheOwner: TComponent); 123 | begin 124 | inherited Create(TheOwner); 125 | StopOnException := True; 126 | 127 | SimpleBOT := TSimpleBotModule.Create; 128 | SimpleBOT.StorageType := stFile; 129 | SimpleBOT.StorageFileName := 'files/carik/carik-userdata.dat'; 130 | SimpleBOT.OnError := @OnErrorHandler; 131 | SimpleBOT.TrimMessage := False; 132 | SimpleBOT.IsStemming := False; 133 | SimpleBOT.StandardWordCheck := False; 134 | end; 135 | 136 | destructor TCarik.Destroy; 137 | begin 138 | SimpleBOT.Free; 139 | inherited Destroy; 140 | end; 141 | 142 | procedure TCarik.WriteHelp; 143 | begin 144 | { add your help code here } 145 | writeln('Usage: ', ExtractFileName(ExeName), ' -h'); 146 | end; 147 | 148 | var 149 | Application: TCarik; 150 | 151 | begin 152 | Config := TMyConfig.Create(nil); 153 | Config.Filename := 'config/config.json'; 154 | 155 | Application := TCarik.Create(nil); 156 | Application.Title:='Carik Console'; 157 | Application.Run; 158 | Application.Free; 159 | end. 160 | -------------------------------------------------------------------------------- /source/common/command_controller.pas: -------------------------------------------------------------------------------- 1 | unit command_controller; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | interface 6 | 7 | uses 8 | carik_webmodule, regexpr_lib, 9 | Classes, SysUtils, fpcgi, fpjson, json_lib, HTTPDefs, fastplaz_handler, 10 | database_lib, string_helpers, dateutils, datetime_helpers, json_helpers; 11 | 12 | {$include ../common/carik.inc} 13 | 14 | type 15 | 16 | { TCommandController } 17 | 18 | TCommandController = class(TCarikWebModule) 19 | private 20 | userIdAsArray: TStrings; 21 | FUserId: string; 22 | function validateMuteDate(ADateAsString: string): string; 23 | procedure prepareData; 24 | procedure commandUserset(); 25 | 26 | public 27 | constructor CreateNew(AOwner: TComponent; CreateMode: integer); override; 28 | destructor Destroy; override; 29 | 30 | procedure Get; override; 31 | procedure Post; override; 32 | procedure Options; override; 33 | end; 34 | 35 | implementation 36 | 37 | uses common; 38 | 39 | function TCommandController.validateMuteDate(ADateAsString: string): string; 40 | begin 41 | Result := ''; 42 | if ADateAsString.IsEmpty then Exit; 43 | 44 | MutedUntil := MutedUntil.FromString(ADateAsString); 45 | if MutedUntil > Now then 46 | Result := ADateAsString; 47 | end; 48 | 49 | procedure TCommandController.prepareData; 50 | begin 51 | userIdAsArray := Explode(FUserId, '-'); 52 | if (userIdAsArray.Count = 1) then 53 | begin 54 | userIdAsArray.Free; 55 | OutputJson(400, ERR_INVALID_PARAMETER); 56 | end; 57 | 58 | if userIdAsArray[0] = '5' then userIdAsArray[0] := 'wa'; 59 | if userIdAsArray[0] = 'tl' then ChannelId := 'telegram'; 60 | if userIdAsArray[0] = 'fb' then ChannelId := 'facebook'; 61 | if userIdAsArray[0] = 'wa' then ChannelId := 'whatsapp'; //whatsapp, public_nlp 62 | if ChannelId.IsEmpty then OutputJson(400, ERR_INVALID_PARAMETER); 63 | FUserId := userIdAsArray[1]; 64 | 65 | if not ClientId.IsEmpty then 66 | SessionPrefix := ClientId + '-'; 67 | 68 | // Set Session 69 | SessionController.SessionPrefix := ChannelId; 70 | SessionController.SessionSuffix := FUserId; 71 | SessionController.ForceUniqueID := FUserId; 72 | SessionController.StartSession; 73 | 74 | SimpleBOT.SessionUserID := userIdAsArray[0] + FUserId; 75 | end; 76 | 77 | procedure TCommandController.commandUserset(); 78 | procedure setUpMute(); 79 | const 80 | VAR_MUTE = 'duration'; 81 | var 82 | muteDuration: string; 83 | begin 84 | muteDuration := RequestAsJson[VAR_MUTE]; 85 | if muteDuration.IsNotEmpty then 86 | begin 87 | muteDuration := Now.IncMinute(muteDuration.AsInteger).AsString; 88 | end; 89 | SimpleBOT.UserData[SessionPrefix + 'mute'] := muteDuration; 90 | end; 91 | begin 92 | setUpMute(); 93 | end; 94 | 95 | constructor TCommandController.CreateNew(AOwner: TComponent; CreateMode: integer 96 | ); 97 | begin 98 | inherited CreateNew(AOwner, CreateMode); 99 | end; 100 | 101 | destructor TCommandController.Destroy; 102 | begin 103 | userIdAsArray.Free; 104 | inherited Destroy; 105 | end; 106 | 107 | // GET Method Handler 108 | procedure TCommandController.Get; 109 | var 110 | s: string; 111 | json: TJSONUtil; 112 | begin 113 | Response.ContentType := 'application/json'; 114 | 115 | FUserId := _GET['userId']; 116 | if FUserId.IsEmpty then OutputJson(400, ERR_INVALID_PARAMETER); 117 | prepareData; 118 | 119 | if Operation = OPERATION_USERSET then 120 | begin 121 | json := TJSONUtil.Create; 122 | json['code'] := Int64(0); 123 | if ClientId = '0' then 124 | json['data/client_id'] := '' 125 | else 126 | json['data/client_id'] := ClientId; 127 | json['data/channel_id'] := ChannelId; 128 | json['data/user_id'] := FUserId; 129 | json['data/prefix'] := SessionPrefix; 130 | json['data/mute'] := validateMuteDate(SimpleBOT.UserData[SessionPrefix + 'mute']); 131 | json['data/last_visit'] := SimpleBOT.UserData['NLP_VISITLAST']; 132 | 133 | Response.Content := json.AsJSON; 134 | json.Free; 135 | Exit; 136 | end; 137 | 138 | OutputJson(1, FAILED); 139 | end; 140 | 141 | // POST Method Handler 142 | procedure TCommandController.Post; 143 | var 144 | s: string; 145 | begin 146 | Response.ContentType := 'application/json'; 147 | 148 | FUserId := _POST['userId']; 149 | if ClientId = '0' then ClientId := _POST['clientid']; 150 | if ClientId.IsEmpty then ClientId := RequestAsJson['clientid']; 151 | if FUserId.IsEmpty then FUserId := RequestAsJson['userId']; 152 | if ClientId.IsEmpty then ClientId := '0'; 153 | if FUserId.IsEmpty then OutputJson(400, ERR_INVALID_PARAMETER); 154 | prepareData; 155 | 156 | if Operation.IsEmpty then Operation := RequestAsJson['op']; 157 | if Operation = OPERATION_USERSET then 158 | begin 159 | commandUserset(); 160 | OutputJson(0, OK + ' ' + Now.AsString + '/' + SessionPrefix); 161 | end; 162 | 163 | OutputJson(1, FAILED); 164 | end; 165 | 166 | // OPTIONS Method Handler 167 | procedure TCommandController.Options; 168 | begin 169 | Response.Code := 204; 170 | Response.Content := ''; 171 | end; 172 | 173 | 174 | end. 175 | 176 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | 2 | 3 | # Carik - Bot Like Human 4 | 5 | ## What is it? 6 | 7 | **Carik** adalah bot messenger yang bisa membantu Anda dalam aktivitas sehari-hari. 8 | 9 | Carik juga memiliki fitur sebagai penjawab pesan sederhana, menanyakan hal-hal yang telah didefinisikan sebelumnya oleh system. 10 | Walaupun memiliki fitur menjawab otomatis, dan belajar suatu definisi kata sederhana, 11 | kecerdasan Bot ini tergantung dari data *entity* dan *intent* yang Anda miliki, serta logic handler yang Anda buat. 12 | 13 | Contoh penggunaan bot sederhana dengan SimpleBOT ini bisa anda coba dari situs [bot.fastplaz.com](http://bot.fastplaz.com) atau bisa melalu aplikasi chat **Telegram**, silahkan hubungi contact *'Fastplaz Bot'*. 14 | 15 | 16 | ## Why use it? 17 | 18 | **Ringan Tanpa Beban** 19 | 20 | **Carik** merupakan turunan dari [SimpleBOT](https://github.com/luridarmawan/SimpleBOT), yang menggunakan [Natural Language Processing (NLP)](https://github.com/luridarmawan/SimpleAI) yang sederhana dari [SimpleAI](https://github.com/luridarmawan/SimpleAI). 21 | 22 | Dibuat dengan sederhana, simple dan ringan. SimpleBOT sendiri adalah _binary application_ sehingga diharapkan akan lebih cepat dan ringan. 23 | 24 | Kompatibel dengan shared hosting cPanel pada umumnya. 25 | 26 | Sedangkan untuk penggunaan custom, cukup dibutuhkan instalasi Apache Web Server regular. 27 | 28 | 29 | ## How to use it 30 | 31 | 32 | ### Requirements 33 | 34 | - [FastPlaz_runtime](http://www.fastplaz.com/) 35 | - [SimpleBOT package](https://github.com/luridarmawan/SimpleAI/) 36 | 37 | ### Instalasi 38 | 39 | **install requirement** 40 | 41 | ```bash 42 | $ mkdir -p Carik/source/vendors 43 | $ cd Carik/source 44 | $ git clone -b development https://github.com/luridarmawan/Carik.git 45 | 46 | # change to branch development 47 | 48 | # install vendors 49 | # change to branch development if needed 50 | 51 | $ cd vendors 52 | $ git clone -b development https://github.com/fastplaz/fastplaz.git 53 | $ git clone -b development https://github.com/luridarmawan/SimpleAI.git 54 | 55 | 56 | ``` 57 | 58 | **Compile dari IDE** 59 | 60 | Jika menggunakan Lazarus, buka file "carik.lpi" dan *compile* file tersebut. 61 | 62 | Akan terbentuk file binary di 'public_html/carik.bin' 63 | 64 | **Compile dari Command-Line** 65 | 66 | ```bash 67 | cd Carik 68 | ./clean.sh 69 | ./build.sh 70 | . 71 | . 72 | ai123.lpr(13,124) 73 | Assembling (pipe) lib/carik.s 74 | Compiling resource lib/carik.or 75 | Linking ../../public_html/carik/carik.bin 76 | . 77 | . 78 | source$ _ 79 | 80 | ``` 81 | 82 | **Custom Build** 83 | 84 | untuk konfigurasi custom, misal untuk perubahan path tempat library berada, bisa dilakukan dengan melakukan modifikasi di file **extra.cfg**. 85 | 86 | **Telegram Bot Installation** 87 | 88 | Cara instalasi bot telegram bisa anda ikuti dari situs offisial dari telegram. 89 | 90 | 91 | 92 | ## Carik USAGE 93 | 94 | Pada dasarnya, Carik bertindak seperti bot pada umumnya, fitur yang ada di SimpleBot ada pula di Carik. Cukup tanyakan kepadanya hal2 tertentu, dia akan menjawabnya, tentu saja selama data-2 pertanyaan sudah dia miliki sebelumnya. 95 | 96 | Beberapa hal yang bisa ditanyakan: 97 | 98 | - greeting 99 | - jam/hari/bulan saat ini 100 | * ```sekarang jam berapa``` 101 | * ```hari apa sekarang``` 102 | - jadwal sholat 103 | * ```jadwal sholat``` 104 | * ```jadwal sholat semarang``` 105 | - whois domain 106 | * ```whois fastplaz.com``` 107 | * ```whois pandi.id lengkap``` 108 | - perhitungan angka 109 | * ```berapa 1+1*5``` 110 | * ```hitung sin(10)/2``` 111 | - arti kata 112 | * ```artinya kehidupan``` 113 | - penerjemahan kalimat (translate) 114 | * ```terjemahin how are you``` 115 | * ```translate apa kabar``` 116 | * ```en id how are you``` 117 | - Pajak Kendaraan Bermotor (hanya untuk area tertentu) 118 | * ```pajak AB 1234 BC``` 119 | 120 | - cek resi pengiriman paket dari kurir: jne, tiki, pos, pandu, jnt, sicepat dan wahana 121 | * ```format: resi [kurir] [koderesi]``` 122 | * ```cek resi jno 12345678``` 123 | - info film 124 | * ```cari info film ada dengan cinta``` 125 | - kurs 126 | * ```1 usd berapa idr``` 127 | - QuickCount Pilkada DKI 2017 128 | * ```pilkada dki``` 129 | 130 | 131 | **beberapa fitur becanda:** 132 | 133 | - cek jadwal 134 | - beli pulsa 135 | 136 | Khusus untuk merekam diskusi, Anda cukup memberikan perintah: 137 | 138 | ``` 139 | @bot catat diskusi 140 | ``` 141 | beberapa kalimat yang bisa digunakan: 142 | 143 | - @bot catat notulen 144 | - @CarikBot rekam obrolan 145 | - @CarikBot mulai rekaman 146 | 147 | bisa langsung dimention, atau dengan me-reply comment bot sebelumnya. 148 | 149 | ## Video Compilasi Source 150 | 151 | [![Video to Compiling Carik](img/compiling.png)](https://www.youtube.com/watch?v=m8n4qijbcGM) 152 | 153 | ## Referensi 154 | 155 | - [Natural Language Processing (NLP) sederhana dari Carik Bot](https://medium.com/@luridarmawan/natural-language-processing-nlp-sederhana-dari-carik-bot-78952b618695) 156 | - [Stemming Word dalam Carik](https://medium.com/@luridarmawan/stemming-word-dalam-carik-da3b802038c8) 157 | - [GPT-3](https://en.wikipedia.org/wiki/GPT-3) 158 | - [ChatGPT-API](https://github.com/transitive-bullshit/chatgpt-api) 159 | - [OpenAI](https://en.wikipedia.org/wiki/OpenAI) 160 | 161 | ## Credits 162 | 163 | Carik Bot is developed by [Luri Darmawan](https://github.com/luridarmawan/) and 20+ amazing contributors. Special thanks to Hastura, Mbah Don and Delli for originally creating Carik character. 164 | 165 | If you found this project interesting, please consider [sponsoring me](https://github.com/sponsors/luridarmawan/). 166 | 167 | -------------------------------------------------------------------------------- /public_html/carik/files/nlp/ai-entities.txt: -------------------------------------------------------------------------------- 1 | [Example] 2 | action=example 3 | say=example 4 | 5 | [WordCencor] 6 | gila=gila|gendeng|crazy|pea|kampret 7 | binatang=asu|anjing|babi 8 | lainnya=tai|taek|eek|pret|setan|kakeane|dancuk|jiancuk 9 | sexuality=kontol|ngentu|bawuk|ngentot 10 | wtf=what the fuck|fuck|wtf 11 | 12 | [Greeting] 13 | hi=hi|hii|hai|hei|halo|hallo|halow|hallow|hellow|hola|hox|hy 14 | salam=salam kenal|salam 15 | yo=yo|yoyoi 16 | jawa=kulonuwun|nuwun 17 | 18 | [SalamMuslim] 19 | salam=assalamualaikum|assalamu'alaikum|assalamualaykum|assalamu'alaykum|assalamu alaikum 20 | salamlengkap=assalamu alaikum wa rahmatullah|assalamu'alaikum wa rahmatullah 21 | 22 | [SalamArabic] 23 | salam1=ﷵ 24 | 25 | [Sapaan] 26 | aku=aku|saya|sy|gue|gwe|gw|akyu|ane|私 27 | kamu=kamu|kmu|mu|kamyu|kau|dikau|engkau|ngkau|anda|lu|loe|ente|sampean|samean 28 | dia=om|mbah|pak|mas|pakdhe|kak|kakak|mas|bu|ibu|dek 29 | kakak=kk 30 | 31 | [HalTerlarang] 32 | narkoba=ganja|inex|narkoba|morfin|candu 33 | miras=bir|wiski|vodka 34 | mabuk=mabuk|mabok 35 | sex=kentu|ngentot|ml|sex|homo|lesbian|lesbi 36 | 37 | [Keadaan] 38 | baik=baik|sehat|alhamdulillah|kuat|semangat|sembuh 39 | buruk=buruk|sakit|demam|capek|lelah|sepi|pusing|pusing2|mual|mual2 40 | 41 | 42 | [Pasangan] 43 | pasangan=jodoh|pasangan 44 | suami=suami|swami|laki|cowo 45 | istri=istri|bini|wife|cewe 46 | pacar=pacar 47 | 48 | [Abaikan] 49 | yuk=dong|yuk 50 | 51 | [TanyaLokasi] 52 | dimana=di mana|dimana 53 | 54 | [Pembayaran] 55 | cicilan=cicilan|cicil|angsuran|angsur|installment|instalment 56 | tunai=tunai 57 | 58 | [Tanya] 59 | tandatanya=\? 60 | siapa=siapa|syapa|sapa 61 | apa=apa|apakah|pa 62 | mengapa=mengapa|ngapa|napa|kenapa|knp|why 63 | berapa=berapa|brp|brapa|piro 64 | bagaimana=bagaimana|gimana|gmn|bgmn|bgm|how 65 | bisa=bisakah|bisa|boleh|bolehkan|bolehkan 66 | mau=mau|bersedia 67 | ngapain=ngapain 68 | kapan=kapan|kpn 69 | 70 | [Perintah] 71 | cari=cariin|carikan|cari|temukan 72 | beli=belikan|beli|blikan|beliin|pesan|pesen|pesan|pesenin|pesanin 73 | jual=jual|jualin 74 | buat=mbuat|buatkan|buat|buwat|buatin 75 | hitung=hitung|hitungkan|hitungin|itungin 76 | ambil=ambil|ambilkan 77 | pergi=pergi 78 | 79 | [Respon] 80 | baik=baik|baiklah|okey|okeh|oke|okelah|ok|sip|sipp|senang|seneng|yoi|terima kasih|terima ksh|makasih|trm ksh|thx|thanks|silahkan|selow|woles|slow|iya|ya|yak|oiyah|tentu|thank|thx|cakep 81 | buruk=mbuh|tauah|tauk|ga tau|ngga tau|entahlah|gaje|gajelas|karepmu|auah|au ah|ga asik|gak asik|gak asyik|goblok|sombong|sontoloyo|asem|terserah|dasar|iyalah 82 | maklum=maklumi|maklum 83 | gemblung=gemblung|gokil|bego|parah|gandeng|songong|setres|stres|stress|ngeyel 84 | 85 | [Logika] 86 | ya=iyak|yak|yak|iyes|yes 87 | tidak=tidak|tdk|nggak|gak|ga|enggak 88 | 89 | [Waktu] 90 | jam=jam 91 | hari=hari|hr 92 | minggu=minggu 93 | bulan=bulan|bln 94 | tahun=tahun|thn 95 | tanggal=tanggal|tgl 96 | waktu=pagi|siang|sore|petang|malam|malem|morning|night 97 | 98 | [Kondisi] 99 | jika=jika|kalau|kalaw|kalo|klo|apabila|bila 100 | 101 | [RutinitasHarian] 102 | makan=makan|mangan|maem|mkan|makanan 103 | minum=minum|mnum|minuman 104 | mandi=mandi|mndi 105 | tidur=tidur|turu|bobo 106 | kerja=kerja|gawe 107 | 108 | [Aktivitas] 109 | laku=lakukan|jalani|perbuat 110 | belajar=belajar|blajar 111 | 112 | [PersonalStatus] 113 | nikah=nikah|menikah|merid|married|meried 114 | single=jomblo|single|gadis|gds|lajang|perjaka|homo|jablai 115 | 116 | [Umur] 117 | umur=umur|usia 118 | umurmu=umurmu 119 | 120 | [JenisKelamin] 121 | laki=laki-laki|laki laki|laki|lanang|lelaki 122 | perempuan=perempuan|gadis|ibu 123 | 124 | [PersonalKnowledge] 125 | tahu=kenal|tau|tahu|ngerti|ngertiin 126 | 127 | [HargaLevel] 128 | mahal=paling mahal|termahal|mahal|mhal 129 | murah=paling murah|termurah|murah|mrah 130 | 131 | [Nominal] 132 | nominal=.*\d 133 | range=kisaran|seharga|seputar|harga 134 | harga=harga|hrga 135 | 136 | [RangeNilai] 137 | minimal=minimal|min|mulai dari|mulai|terendah 138 | maksimal=maksimal|maximal|max|dibawah|di bawah|dibaah|kurang dari|kurang|tidak lebih dari|tdk lebih dr|tidak lebih|tdk lebih|tertinggi 139 | 140 | [Angka] 141 | angka=.*\d 142 | angkasatuan=satu|dua|tiga|empat|lima|enam|tujuh|delapan|sembilan|sepuluh|seratus|seribu|sejuta 143 | 144 | [Satuan] 145 | ribu=ribu|rb 146 | juta=juta|jt 147 | milyar=milyar|milyr|miliar 148 | 149 | [Kencantikan] 150 | baik=ngganteng|ganteng|cantik|keren|hebat|powerful|top|pinter|pintar|cakep 151 | buruk=jelek|songong|gila|budeg|bodoh 152 | 153 | [Perasaan] 154 | tidak=benci|jijay|ga suka|ga seneng 155 | baik=suka|demen|seneng|kesengsem|trisna|love 156 | 157 | [Ekspresi] 158 | baik=haha|hehe|hihi|hoho|wkwk|muachhh|muatih 159 | kaget=eehh|ehh|wow 160 | 161 | [Keraguan] 162 | kok=kok|koq|lhoo|lho|lah|oya|ohya|masa sih|masa 163 | 164 | [Sifat] 165 | baik=baik|super|luar biasa|hebat|keren|cool|pinter|cerdas 166 | buruk=jahat|genit|bodoh|goblok|jelek 167 | 168 | [Figure] 169 | presiden=soekarno|soeharto|sby|jokowi|megawati|prabowo|jkw 170 | pahlawan=pattimura|diponegoro|kartini 171 | jagoan123=ansori|encang|ihdi|oka|abi|ines 172 | dev=peter|bams|bambang|anne|deroh|ratu|yudi|joko 173 | devpascal=indra|tigor|derit|kofa|maskofa 174 | CafeStartup=temmy|gisela|gisel|bontot|wiwin 175 | 176 | [Profesi] 177 | pembantu=pembantu 178 | karyawan=karyawan 179 | programmer=developer|programmer|tukang ketik 180 | prt=pembantu rumah tangga|prt|pembantu rmh tangga 181 | dokter=dokter|dok 182 | swasta=swasta 183 | pns=pegawai negeri|pgw negeri|pegawai negri|pgw negri 184 | 185 | [MelakukanSesuatu] 186 | hubungi=menghubungi|hubungi|ngubungin|kontak 187 | belajar=belajar 188 | ngopi=ngopi 189 | 190 | [Sedang] 191 | sudah=sdh|sudah|sdah|udah 192 | sedang=sedang|sdg|lagi|lg 193 | akan=akan|mau|mo 194 | 195 | [Tolong] 196 | tolong=tolong|tulung|tolongin 197 | help=help 198 | 199 | [NoRespon] 200 | responthx=sama-sama|sama sama|sama|sama2 201 | 202 | [TandaBaca] 203 | tanya=\? 204 | titik=. 205 | koma=, 206 | seru=\! 207 | 208 | -------------------------------------------------------------------------------- /public_html/carik/config/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "systems": { 3 | "sitename": "CarikBOT", 4 | "slogan": "SimpleBOT with SimpleAI and FastPlaz", 5 | "baseurl": "", 6 | "admin_email": "webmaster@carik.id", 7 | "development": false, 8 | "debug": false, 9 | "module_default": "main", 10 | "language_default": "id", 11 | "theme_enable": false, 12 | "theme": "default", 13 | "cache": "none", 14 | "temp": "ztemp", 15 | "error_url": "", 16 | "session_autostart": false, 17 | "session_timeout": 0, 18 | "ffmpeg_path": "./ffmpeg", 19 | "error_redirect": false 20 | }, 21 | "stemming" : { 22 | "dictionary_file" : "files/dictionary.csv", 23 | "nonstandardword_file" : "files/word-nonstandard.txt" 24 | }, 25 | "external_nlp": { 26 | "enable": false, 27 | "nlp": [ 28 | { 29 | "enable": true, 30 | "url": "http://localhost:8080/api/", 31 | "key": "" 32 | }, 33 | { 34 | "enable": true, 35 | "url": "http://ml.carik.local:8008/learning", 36 | "key": "" 37 | } 38 | ] 39 | }, 40 | "suggestion":{ 41 | "enable": false, 42 | "url": "" 43 | }, 44 | "services": { 45 | "knowledgebase_url": "", 46 | "chatlog_url": "", 47 | "joinlog_url": "", 48 | "groupaddlog_url": "", 49 | "groupinfo_url": "", 50 | "groupmember_url": "", 51 | "blacklistcheck_url": "", 52 | "blacklistadd_url": "" 53 | }, 54 | "knowledge_base": { 55 | "url": "", 56 | "chatlog_url": "", 57 | "joinlog_url": "", 58 | "groupaddlog_url": "", 59 | "blacklistcheck_url": "", 60 | "blacklistadd_url": "" 61 | }, 62 | "carik_search": { 63 | "method": "post", 64 | "url": "" 65 | }, 66 | "blacklist": { 67 | "users": [ 68 | {"id": "telegram_user_id", "nama": "Full Name"} 69 | ], 70 | "groups": [ 71 | {"id": "telegram_group_id", "nama": "Group Name"} 72 | ] 73 | }, 74 | "redis": { 75 | "loader_path": "/Users/user/app/redis-loader.sh", 76 | "default": { 77 | "server": "localhost", 78 | "port": 6379, 79 | "timeout": 2500 80 | } 81 | }, 82 | "ai": { 83 | "default": { 84 | "name": "Carik", 85 | "client_id": 1, 86 | "datasource": "file", 87 | "userdata_storage": "file", 88 | "debug": false, 89 | "stemming": true, 90 | "standard_word_check": true, 91 | "reply_disable": false, 92 | "first_session_response": false, 93 | "basedir": "files/nlp/", 94 | "unknown_stats_url": "", 95 | "user_status": { 96 | "client_id": "carik", 97 | "url": "" 98 | }, 99 | "unknown_chat": { 100 | "maximum_retries": 3, 101 | "callback_intent": "UnknownChatCarik", 102 | "mute_duration": 0 103 | }, 104 | "external_nlp": { 105 | "enable": false, 106 | "url": "", 107 | "key": "" 108 | }, 109 | "entities": [ 110 | "main-entities.txt" 111 | ], 112 | "intents": [ 113 | "main-intents.txt", 114 | "others-intents.txt" 115 | ], 116 | "response": [ 117 | "main-response.txt", 118 | "others-response.txt" 119 | ], 120 | "trigger_word": { 121 | "bot_call": ["carik", "bot"], 122 | "meninggal": ["(telah|telah|kemaren|kemarin|tadi|yang) (meninggal|wafat)", "innalillahi"], 123 | "sakit": ["lagi sakit"], 124 | "makan2": ["makan2", "makan-makan"], 125 | "ulang_tahun": ["ulang tahun", "hbd", "birthday", "milad", "met ultah"], 126 | "aamiin": ["aamiin|amiin|aamin|aamien|آمين"] 127 | }, 128 | "spam_word": { 129 | "link": ["\\.cn/","?ref=","t.me/joinchat","shorturl.at","t.me/binaryprofittrader","t.me/etheriumfundsbot",".me/EasyMakeMoneyBot", "clickkkgo.site/"], 130 | "domain": ["akcapitaltrade.com","binanciexchange.com","bitcointrade.com","bitcoinhubbell.com","get.cryptobrowser.site","uermoney.icu","info-dex.com"], 131 | "blockchain": ["mining/"], 132 | "referral": ["referral/","referal/"], 133 | "kuota": ["\\.cf"], 134 | "other_group": ["t.me/ngodingbikinasik"], 135 | "black_word": ["Earn (.*) ether every"] 136 | } 137 | } 138 | }, 139 | "telegram": { 140 | "default": { 141 | "token": "", 142 | "reply_disable": false, 143 | "first_session_response": false, 144 | "whitelist": "" 145 | } 146 | }, 147 | "line": { 148 | "default": { 149 | "token": "", 150 | "reply_disable": false, 151 | "first_session_response": false 152 | } 153 | }, 154 | "facebook": { 155 | "default": { 156 | "token": "", 157 | "reply_disable": false, 158 | "first_session_response": false 159 | } 160 | }, 161 | "google": { 162 | "key": "", 163 | "default": { 164 | "key": "" 165 | } 166 | }, 167 | "googleanalytics": { 168 | "default": { 169 | "tracking_id": "" 170 | } 171 | }, 172 | "zomato": { 173 | "default": { 174 | "url": "", 175 | "key": "" 176 | } 177 | }, 178 | "yandex": { 179 | "default": { 180 | "key": "" 181 | } 182 | }, 183 | "witai": { 184 | "default": { 185 | "token": "" 186 | } 187 | }, 188 | "cognitive": { 189 | "ocr": { 190 | "key": "", 191 | "key2": "" 192 | } 193 | }, 194 | "customvision": { 195 | "default": { 196 | "key": "", 197 | "url": "" 198 | } 199 | }, 200 | "openweathermap": { 201 | "default": { 202 | "key": "" 203 | } 204 | }, 205 | "weatherstack": { 206 | "default": { 207 | "key": "" 208 | } 209 | }, 210 | "klaudless": { 211 | "default": { 212 | "appid": "", 213 | "apikey": "", 214 | "calendar_accountid": "", 215 | "calendar_id": "" 216 | } 217 | }, 218 | "msbotframework": { 219 | "default": { 220 | "client_id": "", 221 | "client_secret": "" 222 | } 223 | }, 224 | "rss": { 225 | "detik": "http://rss.detik.com/index.php/detikcom_nasional", 226 | "sindo": "https://www.sindonews.com/feed", 227 | "antara": "http://www.antaranews.com/rss/top-news", 228 | "tempo": "https://rss.tempo.co/index.php/teco/news/feed/start/0/limit/10/kanal/6", 229 | "okezone": "http://sindikasi.okezone.com/index.php/rss/0/RSS2.0", 230 | "kapanlagi": "https://www.kapanlagi.com/feed/", 231 | "republika": "http://www.republika.co.id/rss" 232 | }, 233 | "carik": { 234 | "path": "files/carik/", 235 | "tts_url": "", 236 | "groups": { 237 | } 238 | }, 239 | "database" : { 240 | "default" : { 241 | "driver" : "MySQL 5.7", 242 | "hostname" : "localhost", 243 | "port" : "", 244 | "username" : "root", 245 | "password" : "root", 246 | "database_name" : "carik", 247 | "prefix" : "", 248 | "library" : "" 249 | } 250 | }, 251 | "mailer": { 252 | "default": { 253 | "hostname": "your.smtp.server", 254 | "username": "your_username", 255 | "password": "the_password", 256 | "smtp_port": "465", 257 | "ssl": true, 258 | "tls": true 259 | } 260 | } 261 | } 262 | -------------------------------------------------------------------------------- /public_html/carik/files/nlp/ai-intents.txt: -------------------------------------------------------------------------------- 1 | [ExamplePattern] 2 | action=example 3 | say=@Example 4 | 5 | [WordCencor] 6 | say=@WordCencor 7 | 8 | [Test1] 9 | say=test 10 | 11 | [ResponBaik] 12 | say=^@Respon:baik 13 | say=^@Respon:maklum 14 | 15 | [ResponBuruk] 16 | say=@Respon:buruk 17 | say=@Logika:tidak @Tanya:bisa 18 | say=@Logika:tidak usah 19 | say=^@Logika:tidak 20 | say=@Respon:gemblung 21 | 22 | [HubungiSupport] 23 | say=@Tanya:bagaimana @Sapaan:aku @MelakukanSesuatu:hubungi support 24 | say=@Tanya:bagaimana @Sapaan:aku @MelakukanSesuatu:hubungi 25 | 26 | [PembantuCari] 27 | say=@Profesi:pembantu @PropertyType:rumah tangga 28 | say=pembantu rumah tangga 29 | 30 | [Sanjungan] 31 | say=@Sapaan:kamu @apapun @Kencantikan:baik 32 | say=@Sapaan:kamu @Kencantikan:baik 33 | say=@Sapaan:kamu @apapun @Sifat:baik 34 | say=@Sapaan:kamu @Sifat:baik 35 | 36 | [Mengeluh] 37 | say=(kok|koq) gitu 38 | say=@Tanya:bagaimana sih 39 | say=capek (ahh|deh) 40 | 41 | [TelegramBotStart] 42 | action=telegram_menu 43 | say=/start 44 | 45 | [ResiPaket] 46 | action=resi_paket 47 | say=resi @vendor @nomor 48 | 49 | [Kamus] 50 | action=kamus 51 | object=kamus 52 | say1=apa itu @word 53 | say2=^@word (artinya|arti|maksud|maksudnya|kamus) 54 | say2=^(artinya|arti|maksud|maksudnya|kamus) @word 55 | say4=@word (artinya|arti|maksud|maksudnya|kamus) 56 | say3=(artinya|arti|maksud|maksudnya|kamus) @word 57 | 58 | [Larangan] 59 | say=(jangan|jgn) @apapun 60 | 61 | [Ajakan] 62 | say=@word (yuk|yuukk|yok) 63 | 64 | [xxxx] 65 | say=xxx 66 | 67 | [SuggestionResponse] 68 | action=suggestion 69 | say=(suggest|saran|teach) @answer : @question 70 | say=(suggest|saran|teach) @answer: @question 71 | 72 | [CarikStart] 73 | action=carik_start 74 | say=mulai (catat|catet) 75 | say=(rekam|catat|catet|mulai|start) (kulwap|obrolan|diskusi|rapat|rekaman|rekam|catatan|catat|notulen|nyatet) 76 | say=(kulwap|obrolan|diskusi|rapat|rekaman|rekam|catatan|catat|notulen|nyatet) (mulai|dimulai|start|dicatat|dicatet) 77 | say=(mulai|start) (kulwap|obrolan|diskusi|rapat|rekaman|rekam|catatan|catat|notulen|nyatet) 78 | 79 | [CarikStop] 80 | action=carik_stop 81 | say=(kulwap|obrolan|diskusi|rapat|rekaman|rekam|catatan|catat|notulen|nyatet) (dihentikan|stop|berhenti) 82 | say=(dihentikan|stop|berhenti|hentikan) (kulwap|obrolan|diskusi|rapat|rekaman|rekam|catatan|catat|notulen|nyatet) 83 | 84 | [CarikSend] 85 | action=carik_send 86 | say=kirimkan rekaman ke @email 87 | say=rekaman kirim ke @email 88 | 89 | [CariCheck] 90 | action=carik_check 91 | say=sedang (nyatet|catet|rekam) 92 | 93 | 94 | [SholatJadwal] 95 | action=jadwal_sholat 96 | say=jadwalsholat @kota 97 | say=jadwalsholat 98 | say=(jadwal|jadual) sholat (untuk|utk|kota) @kota 99 | say=(jadwal|jadual) sholat @kota 100 | say=(jadwal|jadual) sholat 101 | 102 | [Lahir] 103 | object=lahir 104 | say=@Sapaan:kamu lahir 105 | say=@Sapaan:kamu lahirnya 106 | 107 | [NoEnglish] 108 | say=are you speaking english 109 | say=speaking english 110 | say=speak english 111 | 112 | [CariJodoh] 113 | object=jodoh 114 | say=@Perintah:cari @Pasangan 115 | say=@Pasangan:pasangan 116 | 117 | [CariJodohKriteria] 118 | object=jodoh 119 | say=yang @Kencantikan 120 | 121 | [TanyaPasanganSeseorang] 122 | say=@Tanya:siapa @Pasangan @seseorang 123 | say=@Pasangan @seseorang 124 | 125 | [Lulus] 126 | say=@Tanya:kapan @siapapun (lulus|wisusda|meninggal|mati) 127 | say=@Tanya:kapan (lulus|wisuda|meninggal|mati) 128 | 129 | [Nikah] 130 | say=@Tanya:kapan @siapapun @PersonalStatus:status 131 | say=@Tanya:kapan @PersonalStatus:status 132 | 133 | [Kencan] 134 | say=@Sapaan:aku kencan 135 | say=kencan 136 | say=@Sapaan:kamu lamar 137 | say=jalan2 138 | 139 | [HalTerlarang] 140 | say=@Perintah @HalTerlarang 141 | say=@HalTerlarang 142 | 143 | [KeadaanBaik] 144 | say=@Sapaan:kamu @Keadaan:baik 145 | say=@Keadaan:baik 146 | 147 | [KeadaanBuruk] 148 | say=@Sapaan:kamu @Keadaan:buruk 149 | say=@Keadaan:buruk 150 | say=@Keadaan:buruk @apapun 151 | 152 | 153 | [Menghibur] 154 | say=jangan sedih 155 | say=jgn sedih 156 | say=sayang banget 157 | 158 | [TidakPunyaSesuatu] 159 | say=@Logika:tidak punya @apapun 160 | 161 | 162 | [SuruhanPositif] 163 | say=@MelakukanSesuatu:belajar @apapun rajin 164 | 165 | [Ekspresi] 166 | say=^@Ekspresi 167 | say=^@Keraguan 168 | say=ga pa pa 169 | say=ga papa 170 | say=gpp 171 | say=apaan 172 | say=kepo 173 | say=makanya 174 | say=bawel 175 | 176 | [Greeting] 177 | say=@Greeting apa kabar 178 | say=@Greeting 179 | say=selamat @Waktu 180 | say=how are you 181 | say=how are u 182 | say=how r you 183 | say=@Waktu:waktu 184 | 185 | [SalamMuslim] 186 | say=@SalamMuslim 187 | say=@SalamArabic 188 | 189 | [Perpisahan] 190 | say=selamat tinggal 191 | say=sampai ketemu lagi 192 | say=sampai ketemu 193 | say=sampai jumpa 194 | say=bye 195 | 196 | [Perkenalan] 197 | action=define|Name 198 | say=namaku adalah @Name 199 | say=namaku @Name 200 | say=nama @Sapaan:aku @Name 201 | say=@Name nama @Sapaan:aku 202 | say=@Name namaku 203 | say=^nama @Name 204 | say:Name=^@Sapaan:aku @Name 205 | 206 | [PerkenalanEmail] 207 | action=define|Email 208 | say=email ku @Email 209 | say=emailku @Email 210 | say=email sy @Email 211 | say=email @Email 212 | 213 | [StatusAku] 214 | say=masih @PersonalStatus 215 | say=@Sedang:sudah @PersonalStatus 216 | say=@Sapaan:kamu @PersonalStatus 217 | say=@Sapaan @PersonalStatus 218 | 219 | [Aktivitas] 220 | say=@Sapaan:kamu @Sedang @apapun 221 | say=^@Sedang:sedang @apapun 222 | say=@Sedang:sudah @apapun 223 | 224 | [JenisKelamin] 225 | say=@Tanya:kamu @JenisKelamin 226 | 227 | [Umur] 228 | say=@Tanya:berapa @Umur 229 | say=@Umur @Sapaan:kamu 230 | say=@Umur@Sapaan:kamu 231 | say=@Umur 232 | 233 | [TokohSiapa] 234 | say=@Tanya:siapa @apapun @Figure 235 | say=@Tanya:siapa @Figure 236 | say=@Figure @Tanya:siapa 237 | 238 | [SiapaAku] 239 | say=@Tanya:siapa @Sapaan:aku 240 | 241 | [Siapa] 242 | say=perkenalkan diri 243 | say=boleh kenalan 244 | say=mau kenalan 245 | say=@Tanya:siapa @Sapaan:kamu 246 | say=@Sapaan:kamu @Tanya:siapa 247 | say=@Sapaan:kamu itu @Tanya:siapa 248 | say=@Sapaan:kamu itu @Tanya:apa 249 | say=kenalan @Abaikan 250 | say=@Abaikan kenalan 251 | say=^nama @whatever 252 | 253 | [InginTanya] 254 | say=mau (t|n)anya 255 | say=boleh (t|n)anya 256 | 257 | 258 | [TanyaLokasi] 259 | object=location 260 | say=rumah @Sapaan:kamu @Tanya:dimana 261 | say=rumah@Sapaan:kamu @Tanya:dimana 262 | say=@TanyaLokasi rumah @Sapaan:kamu 263 | say=@TanyaLokasi rumahmu 264 | say=@TanyaLokasi rumah 265 | say=@TanyaLokasi @Sapaan:kamu 266 | say=@Sapaan:kamu @TanyaLokasi 267 | 268 | [Kabar] 269 | say=@Tanya:bagaimana kabar@Sapaan:kamu 270 | say=@Tanya:bagaimana kabar 271 | say=@Tanya:bagaimana @Sapaan:kamu 272 | say=@Tanya:apa kabar@Sapaan:kamu 273 | say=@Tanya:apa kabar 274 | say=@Sapaan:kamu @Tanya:bagaimana 275 | say=kabar@Sapaan:kamu @Tanya:bagaimana 276 | say=kabar @Tanya:bagaimana 277 | 278 | [Cuaca] 279 | action=cuaca 280 | say=@Tanya:bagaimana cuaca 281 | say=cuaca @Tanya 282 | say=suasana @Tanya:bagaimana 283 | say=cuaca 284 | 285 | [Angka] 286 | action=angka 287 | say=@Angka @Satuan 288 | say=@berapapun @Satuan 289 | 290 | [UngkapanBaik] 291 | say=@Sapaan @Sifat:baik 292 | say=@Sifat:baik 293 | say=asik @Logika:tidak 294 | 295 | [UngkapanBuruk] 296 | say=@Sapaan @Sifat:buruk 297 | say=@Sifat:buruk 298 | 299 | [Waktu] 300 | say=@Tanya @Waktu 301 | say=@range @Waktu:-waktu @Tanya:berapa 302 | say=@range @Waktu:-waktu @Tanya:apa 303 | say=@Waktu:-waktu @Tanya:berapa 304 | say=@Waktu:-waktu @Tanya:apa 305 | 306 | [CantikGanteng] 307 | boundary=false 308 | say=@apapun @Kencantikan ya 309 | say=@apapun @Kencantikan ga 310 | say=@apapun @Kencantikan gak 311 | 312 | [YangPaling] 313 | say=yang paling @apapun 314 | say=paling @apapun 315 | 316 | [TanyaTentangTokoh] 317 | say=@Sapaan:kamu @PersonalKnowledge @apapun @Figure 318 | say=@Sapaan:kamu @PersonalKnowledge @Figure 319 | say=@PersonalKnowledge @sebutan @Figure 320 | say=@PersonalKnowledge @Figure 321 | 322 | [TanyaTentangTokohTidakDikenal] 323 | say=@Tanya:siapa @siapapun 324 | say=@Sapaan:kamu @PersonalKnowledge @siapapun 325 | say=@PersonalKnowledge @siapapun 326 | 327 | [LoremIpsum] 328 | say=lorem ipsum 329 | say=loremipsum 330 | 331 | [Math] 332 | action=math 333 | object=berhitung 334 | boundary=false 335 | say=@Tanya:berapa @Formula 336 | say=@Perintah:hitung @Formula 337 | 338 | 339 | [TanyaSeandainya] 340 | say=@Tanya:bagaimana @Kondisi:jika @apapun 341 | 342 | [TidakYakin] 343 | say=@apapun @Logika:tidak @PersonalKnowledge:tahu 344 | say=beneran 345 | 346 | [Deskripsi] 347 | action=define 348 | say=@Key itu adalah @Value 349 | say=@Key adalah @Value 350 | say=@Key adl @Value 351 | say=@Key itu @Value 352 | say=@Key = @Value 353 | say=@Key=@Value 354 | 355 | [KenapaDisimpan] 356 | say=@Tanya:mengapa kok disimpan 357 | say=@Tanya:mengapa @apapun 358 | 359 | [telolet] 360 | say=om telolet om 361 | say=omteloletom 362 | say=telolet 363 | 364 | [DomainWhois] 365 | action=domain_whois 366 | say=whois domain @domain @option 367 | say=whois domain @domain 368 | say=whois @domain @option 369 | say=whois @domain 370 | say=who is @domain 371 | 372 | [Cari] 373 | action=cari 374 | say=@Perintah:cari 375 | 376 | [EmailBuat] 377 | object=email 378 | say=@Perintah:buat @Sapaan:aku email 379 | say=@Perintah:buat email 380 | 381 | [MakanBuat] 382 | object=makanan 383 | say=@Perintah:buat @Sapaan:aku @RutinitasHarian:makan 384 | say=@Perintah:buat @Sapaan:aku @RutinitasHarian:minum 385 | say=@Perintah:buat @RutinitasHarian:makan 386 | say=@Perintah:buat @RutinitasHarian:minum 387 | 388 | [MakanBeli] 389 | action=footorder 390 | object=makanan 391 | say=@Perintah:beli @Sapaan:aku @RutinitasHarian:makan 392 | say=@Perintah:beli @Sapaan:aku @RutinitasHarian:minum 393 | say=@Perintah:beli @RutinitasHarian:makan 394 | say=@Perintah:beli @RutinitasHarian:minum 395 | 396 | [PulsaBeli] 397 | action=pulsaorder 398 | object=pulsa 399 | say=@Perintah:beli @Sapaan:aku pulsa 400 | say=@Perintah:beli pulsa 401 | 402 | [MintaTolong] 403 | say=@Tolong 404 | 405 | [BisaApa] 406 | say=bisa @Sapaan:kamu @Lakukan 407 | say=@Sapaan:kamu bisa @Tanya:apa 408 | say=@Tanya:bisa @Tanya:apa 409 | say=@Tanya:bisa @apapun 410 | 411 | [Hadir] 412 | say=ternyata ada di sini 413 | say=ternyata ada disini 414 | say=ada di sini ternyata 415 | say=ada disini ternyata 416 | 417 | [KataTanyaSaja] 418 | say=^@Tanya 419 | say=@Tanya:ngapain 420 | 421 | [PerintahSaja] 422 | say=@Perintah 423 | 424 | [NoRespon] 425 | say=^@NoRespon 426 | say=emailnya disimpan 427 | 428 | [TandaBaca] 429 | say=^@TandaBaca 430 | 431 | [Browse] 432 | action=url|post|http://local-echo.fastplaz.com/?var1=value 433 | say=browse @whatever 434 | 435 | -------------------------------------------------------------------------------- /source/common/carik.inc: -------------------------------------------------------------------------------- 1 | const 2 | CANCEL = 'CANCEL'; 3 | DEFAULT_CHANNEL_ID = '1'; 4 | TELEGRAM_CHANNEL_ID = '2'; 5 | FACEBOOK_CHANNEL_ID = '3'; 6 | LINE_CHANNEL_ID = '4'; 7 | WHATSAPP_CHANNEL_ID = '5'; 8 | SKYPE_CHANNEL_ID = '6'; 9 | SLACK_CHANNEL_ID = '7'; 10 | ANDROID_CHANNEL_ID = '8'; 11 | IOS_CHANNEL_ID = '9'; 12 | INSTAGRAM_CHANNEL_ID = '10'; 13 | TELEGRAM_USERBOT_CHANNEL_ID = '11'; 14 | 15 | WHATSAPP_BUSINESS_CHANNEL_ID = '12'; 16 | SMS_CHANNEL_ID = '13'; 17 | TWITTER_CHANNEL_ID = '14'; 18 | DUALSPACE_CHANNEL_ID = '15'; 19 | SIGNAL_CHANNEL_ID = '16'; 20 | BIP_CHANNEL_ID = '17'; 21 | ZOOM_CHANNEL_ID = '18'; 22 | DISCORD_CHANNEL_ID = '19'; 23 | LIVECHAT_CHANNEL_ID = '20'; 24 | 25 | YES_COMMAND : array [0..4] of string = ('YES', 'YA', 'OK', 'Y', 'SUDAH'); 26 | NO_COMMAND : array [0..5] of string = ('NO', 'N', 'TIDAK', 'TDK', 'T', 'BELUM'); 27 | 28 | BOTNAME_DEFAULT = 'Carik'; 29 | CONFIG_BOTNAME = 'ai/default/name'; 30 | CONFIG_CLIENT_ID = 'ai/default/client_id'; 31 | CONFIG_REPLY_DISABLE = 'ai/default/reply_disable'; 32 | CONFIG_FIRST_SESSION_RESPONSE = 'ai/default/first_session_response'; 33 | 34 | KNOWLEDGEBASE_URL = 'services/knowledgebase_url'; 35 | CHATLOG_URL = 'services/chatlog_url'; 36 | JOINLOG_URL = 'services/joinlog_url'; 37 | GROUPADDLOG_URL = 'services/groupaddlog_url'; 38 | GROUPMEMBER_URL = 'services/groupmember_url'; 39 | GROUPINFO_URL = 'services/groupinfo_url'; 40 | BLACKLISTCHECK_URL = 'services/blacklistcheck_url'; 41 | BLACKLISTADD_URL = 'services/blacklistadd_url'; 42 | BLACKLIST_GLOBAL_FILENAME = 'files/blacklist-global.txt'; 43 | BLACKLIST_FILENAME = 'files/blacklist.txt'; 44 | 45 | 46 | USERSTATUS_URL = 'ai/default/user_status/url'; 47 | USERSTATUS_CLIENTID = 'ai/default/user_status/client_id'; 48 | UNKNOWN_STATS_URL = 'ai/default/unknown_stats_url'; 49 | EXTERNAL_NLP_ENABLE = 'ai/default/external_nlp/enable'; 50 | EXTERNAL_NLP_URL = 'ai/default/external_nlp/url'; 51 | EXTERNAL_NLP_USEGPT = 'ai/default/external_nlp/use_gpt'; 52 | SUGGESTION_ENABLE = 'suggestion/enable'; 53 | SUGGESTION_URL = 'suggestion/url'; 54 | 55 | UNKNOWNCHAT_RETRIES = 'ai/default/unknown_chat/maximum_retries'; 56 | UNKNOWNCHAT_CALLBACK = 'ai/default/unknown_chat/callback_intent'; 57 | UNKNOWNCHAT_MUTE_DURATION = 'ai/default/unknown_chat/mute_duration'; 58 | 59 | CARIKSEARCH_URL = 'carik_search/url'; 60 | CARIKSEARCH_TOKEN = 'carik_search/token'; 61 | 62 | CLARIFAI_TOKEN = 'clarifai/default/token'; 63 | CLARIFAI_CLIENTID = 'clarifai/default/client_id'; 64 | CLARIFAI_CLIENTSECRET = 'clarifai/default/client_secret'; 65 | 66 | CUSTOMVISION_KEY = 'customvision/default/key'; 67 | CUSTOMVISION_URL = 'customvision/default/url'; 68 | 69 | TELEGRAM_TOKEN = 'telegram/default/token'; 70 | TELEGRAM_WHITELIST = 'telegram/default/whitelist'; 71 | TELEGRAM_BOT_REPLY_DISABLE = 'telegram/default/reply_disable'; 72 | TELEGRAM_BOT_FIRST_SESSION_RESPONSE = 'telegram/default/first_session_response'; 73 | FACEBOOK_TOKEN = 'facebook/default/token'; 74 | FACEBOOK_BOT_REPLY_DISABLE = 'facebook/default/reply_disable'; 75 | FACEBOOK_BOT_FIRST_SESSION_RESPONSE = 'facebook/default/first_session_response'; 76 | LINE_TOKEN = 'line/default/token'; 77 | LINE_BOT_REPLY_DISABLE = 'line/default/reply_disable'; 78 | LINE_BOT_FIRST_SESSION_RESPONSE = 'line/default/first_session_response'; 79 | 80 | WITAI_TOKEN = 'witai/default/token'; 81 | GOOGLE_KEY = 'google/default/key'; 82 | GOOGLEANALYTICS_TRACKING_ID = 'googleanalytics/default/tracking_id'; 83 | ZOMATO_URL = 'zomato/default/url'; 84 | ZOMATO_KEY = 'zomato/default/key'; 85 | YANDEX_KEY = 'yandex/default/key'; 86 | COGNITIVE_OCR_TOKEN = 'cognitive/ocr/key'; 87 | OPENWEATHERMAP_KEY = 'openweathermap/default/key'; 88 | WEATHERSTACK_KEY = 'weatherstack/default/key'; 89 | IBACOR_TOKEN = 'ibacor/default/token'; 90 | RAJAONGKIR_TOKEN = 'rajaongkir/default/key'; 91 | 92 | PORTALPULSA_USERID = 'PortalPulsa/default/userid'; 93 | PORTALPULSA_KEY = 'PortalPulsa/default/key'; 94 | PORTALPULSA_SECRET = 'PortalPulsa/default/secret'; 95 | 96 | 97 | 98 | KLAUDLESS_APPID = 'klaudless/default/appid'; 99 | KLAUDLESS_APIKEY = 'klaudless/default/apikey'; 100 | KLAUDLESS_CALENDAR_ACCOUNTID = 'klaudless/default/calendar_accountid'; 101 | KLAUDLESS_CALENDAR_ID = 'klaudless/default/calendar_id'; 102 | 103 | MASKOFA_SHALAT_SESSIONID = 'maskofa/jadwalshalat/sessionid'; 104 | MASKOFA_SHALAT_CITYLISTS = 'maskofa/jadwalshalat/citylists'; 105 | 106 | MSBOTFRAMEWORK_CLIENT_ID = 'msbotframework/default/client_id'; 107 | MSBOTFRAMEWORK_CLIENT_SECRET = 'msbotframework/default/client_secret'; 108 | 109 | FFMPEG_PATH = 'systems/ffmpeg_path'; 110 | VOICE_TMP_PATH = 'ztemp/voice/'; 111 | 112 | CMD_FULL_IMAGE_ANALYZE = 'full image analyze'; 113 | CMD_IMAGE_TRANSLATION = 'image translation'; 114 | 115 | CARIK_TTS_URL = 'carik/tts_url'; 116 | CARIK_TTS_TOKEN = 'carik/tts_token'; 117 | 118 | RUMAH123_API_URL = 'rumah123/default/api_url'; 119 | RUMAH123_API_CLIENT_TYPE = 'rumah123/default/api_client_type'; 120 | RUMAH123_LISTING_MAX = 3; 121 | 122 | PAJAKMOTOR_API = 'pajakmotor/api_url'; 123 | 124 | STEMMING_ENABLED = 'ai/default/stemming'; 125 | STANDARDWORD_CHECKING = 'ai/default/standard_word_check'; 126 | 127 | TRIGGER_INTERVAL = 60; 128 | TRIGGER_SESSION_PREFIX = 'TRIGGER_'; 129 | 130 | // Quick Replay / Button 131 | QUICK_REPLY_IMAGE_DEFAULT = 'https://listimg.pinclipart.com/picdir/s/337-3378299_vector-drawing-transparent-background-green-button-icon-clipart.png'; 132 | 133 | // internal command carik 134 | CMD_POST_RICH = 'post-rich'; 135 | CMD_JSON_RICH = 'json-rich'; 136 | CommandList: array [1..2] of string = 137 | (CMD_POST_RICH, CMD_JSON_RICH); 138 | 139 | NEW_MEMBER_INTERVAL_POST_PERMITTED = 20; 140 | SPAM_SCORE_THRESHOLD = 80; 141 | SPAM_WORD = 'ai/default/spam_word'; 142 | SPAM_CAS_OFFENSE = 1; // api.cas.chat 143 | 144 | GROUP_DATA_FILENAME = 'files/carik/carik-groupdata.dat'; 145 | CALLBACK_QUERY_TIMEOUT = 5; // 5 minutes 146 | CALLBACK_QUERY_TIMEOUT_PREFIX = 30; // 5 minutes 147 | MESSAGE_TYPE = 'message_type'; 148 | MESSAGE_ACTION_TYPE = 'action_type'; 149 | MESSAGE_ACTION_DATE = 'action_date'; 150 | MESSAGE_ACTION_NAME = 'action_name'; 151 | MESSAGE_ACTION_LEVEL = 'action_level'; 152 | MESSAGE_ACTION_IS_MAIN = 'action_is_main'; 153 | MESSAGE_ACTION_URL = 'action_url'; 154 | MESSAGE_ACTION_DATA_ = 'action_data_'; 155 | MESSAGE_ACTION_COUNT = 'action_count'; 156 | MESSAGE_ACTION_SUFFIX = 'action_suffix'; 157 | ACTION_ERR_NLP_TOOBIG = 'action_err_too_big'; 158 | // Pilihan menu: 159 | //ACTION_CAPTION = '\nᴩɪʟɪʜᴀɴ:'; 160 | ACTION_CAPTION = '\nKetik *Nomor* sesuai dengan pilihan berikut:'; 161 | ACTION_SUFFIX = '\nContoh, untuk memilih menu *%s*, ketik: *1*'; 162 | NLP_ERROR_COUNT_MAX = 2; 163 | NLP_DEFAULT_WEIGHT = 100; 164 | LABEL_NLP_ERROR_COUNT = 'nec'; 165 | 166 | EXTERNAL_ACCESS_TIMEOUT = 5000; 167 | EXTERNAL_NLP_TIMEOUT = 30000; 168 | GPT_TIMEOUT_DEFAULT = 60000; 169 | ERR_TIMEOUT_MESSAGE = 'Maaf, saat ini layanan belum bisa diakses. Coba lagi beberapa saat lagi.'; 170 | ERR_INVALID_PARAMETER = 'Invalid parameter.'; 171 | ERR_INVALID_METHOD = 'Invalid method.'; 172 | 173 | OPERATION_USERSET = 'userset'; 174 | SPAM_CHECK_GREETING = '"Hi Human, silakan klik tombol ini agar anda tidak dianggap sebagai spammer."'; 175 | 176 | // Form Input Handler 177 | PREVIOUS_ACTION = 'previous_action'; 178 | CURRENT_ACTION = 'current_action'; 179 | WAITING_INPUT = 'waiting_input'; 180 | WAITING_INPUT_DATE = 'waiting_input_date'; 181 | FORM_INPUT_TIMEOUT = 5; // 5 minutes 182 | FORM_SESSION = 'form_session'; 183 | FORM_SUBMIT_TIMEOUT = 20000; // 20 detik 184 | FORM_INPUT_TIMEOUT_MAX = 60; // 60 minutes 185 | FORM_INPUT_RESET_CODE = '#'; 186 | FORM_INPUT_RELOAD_CODE = '!'; 187 | FORM_INPUT_EXPIRED = '\nSebelumnya kamu sempat melakukan pengisian form, tapi sayang batas waktu pengisian sudah berakhir.\n\n'; 188 | FORM_INPUT_HASHTAG_CANCEL = '\n*Ketik # untuk membatalkan.*' 189 | + '\n*Ulangi* jawaban jika %botname% lama memberikan respon, atau ketik "*'+FORM_INPUT_RELOAD_CODE+'*" (tanda seru).'; 190 | FORM_INPUT_HASHTAG_CANCEL2 = '\nAtau ketik # untuk membatalkan.' 191 | + '\n*Ulangi* jawaban jika %botname% lama memberikan respon, atau ketik "*'+FORM_INPUT_RELOAD_CODE+'*" (tanda seru).'; 192 | FORM_INPUT_HASHTAG_CANCEL3 = '\nSilakan ketikkan informasi yang benar, atau ketik *#* untuk membatalkan.'; 193 | FORM_INPUT_CANCEL = 'Baik, pengisian form %s telah dibatalkan.\nTerima kasih.'; 194 | FORM_INPUT_DATE_FORMAT = '\nTulis dalam format tgl/bln/tahun\nMisal: 17/08/1945'; 195 | FORM_INPUT_OPTION_FORMAT = '\n\nTulis dalam angka sesuai pilihan di atas'; 196 | FORM_INPUT_FILENAME = 'form_filename'; 197 | FORM_INPUT_TITLE = 'input_title'; 198 | FORM_INPUT_NAME = 'input_name'; 199 | FORM_INPUT_TYPE = 'input_type'; 200 | FORM_INPUT_VALUE_MAX = 'input_value_max'; 201 | FORM_INPUT_VALUE_MIN = 'input_value_min'; 202 | FORM_INPUT_LENGTH_MAX = 'input_length_max'; 203 | FORM_INPUT_LENGTH_MIN = 'input_length_min'; 204 | FORM_INPUT_VALIDATION_URL = 'input_validation_url'; 205 | FORM_INPUT_CANCELATION_KEYWORD = 'input_cancelation_keyword'; 206 | FORM_INPUT_OPTION_COUNT = 'input_option_count'; 207 | //FORM_INDEX = 'form_index'; 208 | FORM_TOPIC = 'form_topic'; 209 | FORM_LAST_MESSAGE_ID = 'form_last_message_id'; 210 | FORM_QUESTION = 'form_question'; 211 | FORM_QUESTION_TOTAL = 'form_question_total'; 212 | FORM_PATH = DirectorySeparator + 'form' + DirectorySeparator; 213 | FORM_DATA = 'fdata_'; 214 | FORM_ERR_FORMAT_DATE = 'Format jawaban tidak sesuai, pastikan Anda memasukkan tanggal yang benar, format DD/MM/YYYY.\nContoh: 17/08/1945'; 215 | FORM_ERR_FORMAT_URL = 'Jawaban tidak sesuai, pastikan *URL* yang anda masukkan sudah *benar*.'; 216 | FORM_ERR_FORMAT_EMAIL = 'Jawaban tidak sesuai, pastikan *email* yang anda masukkan sudah *benar*.'; 217 | FORM_ERR_FORMAT_NUMERIC = 'Jawaban tidak sesuai, pastikan yang anda masukkan berformat angka/bilangan'; 218 | FORM_ERR_FORMAT_BOOLEAN = 'Jawaban tidak sesuai, pastikan anda menjawab "Y" atau "T".'; 219 | FORM_ERR_FORMAT_OPTION = 'Jawaban tidak sesuai, pastikan yang anda masukkan berformat angka sesuai pilihan di atas.'; 220 | FORM_ERR_FORMAT_OPTION_INVALID = 'Jawaban tidak sesuai, pastikan angka sesuai dengan pilihan di atas.'; 221 | FORM_ERR_LENGTH_MAX = 'Jawaban tidak sesuai, maksimum %d karakter.'; 222 | FORM_ERR_LENGTH_MIN = 'Jawaban tidak sesuai, minimum %d karakter.'; 223 | FORM_ERR_VALUE_MAX = 'Jawaban tidak sesuai, nilai maksimum adalah %d.'; 224 | FORM_ERR_VALUE_MIN = 'Jawaban tidak sesuai, nilai minimum adalah %d.'; 225 | FORM_ERR_CANCELATION_KEYWORD = '\nKetik "*%s*" untuk mengulang.'; 226 | FORM_ERR_SUBMIT_FAILED = 'Mohon maaf, data Anda gagal dikirim. Silakan coba lagi nanti.'; 227 | FORM_ERR_SUBMIT_EXCEPTION = 'Maaf, terjadi kegagalan dalam pengiriman data. Silakan coba lagi nanti.'; 228 | FORM_ERR_TIMEOUT = 'Maaf, kalau jawaban ini untuk memilih menu, sepertinya waktunya sudah habis. Silakan coba ulangi lagi.\nTerima kasih\n'; 229 | 230 | -------------------------------------------------------------------------------- /public_html/carik/files/nlp/ai-response.txt: -------------------------------------------------------------------------------- 1 | [Test1] 2 | say=hai %Name% 3 | say=wow 4 | 5 | [Introduction] 6 | aboutme=\nPerkenalkan, saya adalah robot penjawab pesan otomatis.\nSaya akan berusaha membantu anda.\nMohon Maaf jika ada yang kurang bisa saya pahami nanti. 7 | firstsession=\n\nSepertinya kita belum pernah bertemu. 8 | secondsession=Senang bisa berjumpa lagi dengan anda. 9 | 10 | [WordCencor] 11 | say=Mungkin bisa digunakan alternatif kalimat yang lain. 12 | say=Maaf, sepertinya akan lebih baik jika menggunakan kata-kata yg lebih sopan 13 | say=Maaf jika pada kondisi tertentu, sepertinya saya tidak merespon Anda. 14 | say=Sayang sekali, mungkin bisa gunakan kata-kata yg lebih baik 15 | 16 | [Greeting] 17 | say=Hi, selamat %time_session% ... 18 | say=Halo, selamat %time_session% ... 19 | say=Hi, salam jumpa ... 20 | say=Hai juga. Kabar baik di sini, semoga kabar baik juga di sana 21 | say=Selamat %time_session% ... 22 | 23 | [SalamMuslim] 24 | say=Wa alaikumsalam 25 | say=Wa alaikumsalam wr wb 26 | say=Wa alaikumsalam Warahmatullahi Wabarakatuh 27 | 28 | [Perpisahan] 29 | say=Sampai ketemu lagi 30 | say=Terima kasih, sampai jumpa lagi 31 | say=Bye, terima kasih 32 | say=bye bye, thanks 33 | 34 | [nonewithobject] 35 | say=... maaf, apakah kita masih membicarakan tentang %object% ? 36 | say=ini masih tentang %object% ? 37 | say=maaf belum paham, ini masih pembicaraan tentang %object% ? 38 | 39 | [none] 40 | say=... maaf jika saya belum banyak memahami kata2 yang ada 41 | say=... percakapan ini kami simpan dahulu, untuk perbendaharaan kata2 saya 42 | say=... bagaimana? 43 | say=... boleh diulang lagi? 44 | 45 | [Waktu] 46 | say=%time% 47 | 48 | [HubungiSupport] 49 | say=silahkan hubungi info kontak yang tercantum di halaman situs kami 50 | say=coba hubungi nomor telpon atau email yang tercantum di halaman situs kami 51 | 52 | [Siapa] 53 | say=Saya adalah BOT. Mesin penjawab otomatis yang akan berkomunikasi singkat dengan Anda. 54 | say=Saya %AIName%, BOT Chat. Jika ada pertanyaan yang lebih spesifik, sebaiknya menghubungi layanan support yang lainnya. 55 | say=Anda boleh panggil saya %AIName% 56 | say=Saya mesin AI, panggil saya %AIName%. \n\nUntuk hal yang lebih spesifik, silahkan hubungi support kami. 57 | 58 | [BisaApa] 59 | say=Saya adalah BOT. saya coba sebisanya 60 | say=Saya masih belajar, masih belum bisa apa2 61 | say=Mungkin saat ini belum 62 | 63 | [SiapaAku] 64 | say=Anda pelanggan kami 65 | say=maaf jika saya belum mengenal anda dengan baik 66 | say=mungkin bisa diperkenalkan, Anda siapa? 67 | say=.......... 68 | 69 | [KenapaDisimpan] 70 | say=untuk perbendaharaan kata2 saya nanti 71 | say=untuk saya pelajari nanti, agar lebih responsif meresepon anda 72 | say=saya masih belajar, masih perlu informasi lebih banyak lagi 73 | 74 | [JenisKelamin] 75 | say=Sepertinya tidak relevan saya untuk menjawabnya 76 | say=Apakah ada urgensinya untuk menjawab ini 77 | say=Saya ini mesin otomasi, status tentang saya sepertinya tidak perlu dipertanyakan 78 | say=Saya ROBOT, status tentang saya seharusnya bukan jadi masalah 79 | say=Seandainya saja menjadi yang mudah untuk disampaikan :( 80 | 81 | [Umur] 82 | say=saya masih muda sekali 83 | say=baru seumur jagung 84 | say=bingung menjawabnya 85 | say=belum seberapa sih 86 | 87 | [StatusAku] 88 | say=Sepertinya tidak relevan saya untuk menjawabnya 89 | say=Apakah ada urgensinya untuk menjawab ini 90 | say=Saya ini mesin otomasi, status tentang saya sepertinya tidak perlu dipertanyakan 91 | say=Saya ROBOT, status tentang saya seharusnya bukan jadi masalah 92 | say=Seandainya saja menjadi yang mudah untuk disampaikan :( 93 | 94 | [Aktivitas] 95 | say=mempelajari tentang AI 96 | say=menikmakti kehidupan ini 97 | say=berharap bisa leluasa berinteraksi seperti anda 98 | say=senang seandainya bisa seperti orang-orang yang lain 99 | 100 | [TanyaLokasi] 101 | say=Tidak jauh kok 102 | say=Saya bisa ada dimana saja 103 | say=Hhhmm... agak sulit juga menjawabnya... 104 | 105 | [TokohSiapa] 106 | say=sepertinya dia %Figure% 107 | 108 | [CantikGanteng] 109 | say=kurang tau juga 110 | say=sulit memperkirakannya 111 | say=mesti dipikir-pikir dulu 112 | say=saya kurang yakin 113 | say=entahlah ... 114 | 115 | [YangPaling] 116 | say=kurang tau juga 117 | say=mungkin Anda? 118 | say=jangan-jangan Anda? 119 | say=aku dong yang paling cuakeppp... muachhh 💋 120 | say=sulit memperkirakannya 121 | say=mesti dipikir-pikir dulu 122 | say=yang pasti bukan saya 123 | say=sepertinya bukan Anda 124 | 125 | [TanyaTentangTokoh] 126 | say=Sepertinya tokoh terkenal 127 | say=Terdengar familiar 128 | say=Banyak orang mengenalnya 129 | say=Layak untuk jadi panutan 130 | say=Prestasinya luar biasa 131 | 132 | [TanyaTentangTokohTidakDikenal] 133 | say=Maaf, sepertinya saya belum pernah jumpa dia 134 | say=Belum pernah jumpa dia 135 | say=Kurang tau juga 136 | say=Orang penting yaa ... 137 | say=Belum familiar dengan dia 138 | say=mmmmmhhh.... saya harus cari dulu .. 139 | 140 | [TanyaDiriSendiriPositif] 141 | say=Entahlah ... 142 | say=Saya tidak dalam posisi untuk menyatakan itu 143 | say=Kerendehan hati sungguh amat sangat dihargai 144 | say=eheemmm.... 145 | say=Banyak orang bilang demikian 146 | 147 | [TanyaDiriSendiriNegatif] 148 | say=Entahlah ... 149 | say=Saya tidak dalam posisi untuk menyatakan itu 150 | say=Ada baiknya kita mesti percaya diri 151 | say=Sepantasnya harus meyakini diri 152 | 153 | [Ekspresi] 154 | say=hehehe 155 | say=hhmm... 156 | say=:) 157 | 158 | [Sanjungan] 159 | say=Terima kasih, semoga demikian juga dengan kamu 160 | say=Semoga tidak membuat saya lupa diri 161 | say=Kerendehan hati sungguh amat sangat dihargai 162 | say=Demikian juga dengan kamu 163 | say=Harapan saya bisa memberikan yang selalu lebih baik 164 | 165 | [Mengeluh] 166 | say=Maaf 167 | say=Hanya berusaha memberikan yang terbaik 168 | 169 | [SuruhanPositif] 170 | say=Saya akan coba melakukan dengan lebih baik 171 | say=Terima kasih, mohon bimbingannya 172 | say=Siap, semoga bisa saya jalani 173 | say=Mohon dukungannya. terima kasih 174 | 175 | [PernyataanSuka] 176 | say=Entahlah ... 177 | say=Kerendehan hati sungguh amat sangat dihargai 178 | say=eheemmm.... 179 | say=Banyak orang bilang demikian 180 | say=Demikian juga dengan kamu 181 | 182 | [MelakukanSesuatu] 183 | say=Sepertinya menarik 184 | say=Sepertinya menyenangkan 185 | say=Nikmat sekali sepertinya 186 | say=Boleh juga 187 | 188 | [Ajakan] 189 | say=Sepertinya menarik 190 | say=Sepertinya menyenangkan 191 | say=Nikmat sekali sepertinya 192 | say=Boleh juga 193 | 194 | [Kabar] 195 | say=Saya baik-baik saja 196 | say=Semangat sekali hari ini 197 | say=sehat 198 | say=Kabar baik di sini 199 | 200 | [Cuaca] 201 | say=Sepertinya menyenangkan 202 | say=Terasa sejuk disini 203 | say=Cerah secerah harapan 204 | say=Nyaman rasanya 205 | 206 | [Keraguan] 207 | say=begitulah ... 208 | say=Mesti berposotif thingking 209 | 210 | [PerkenalanResponse] 211 | say=Hi %Name%, terima kasih 212 | say=%Name%, sepertinya nama yang familiar 213 | say=%Name%, nama yang menarik 214 | say=%Name%, terdengar familiar 215 | 216 | [PerkenalanEmailResponse] 217 | say=Hi %Name%, email anda (%Email%) telah kami simpan 218 | 219 | [TanyaEmailResponse] 220 | say=Hi %Name%, email anda (%Email%) telah kami simpan. 221 | 222 | [DeskripsiResponse] 223 | say=Informasi tentang %Key% akan saya pelajari dulu 224 | say=baiklah... saya coba memahami dulu tentang %Key% 225 | say=hal baru untuk saya.\nsaya akan simpan dulu %Key% di perbendaharaan saya. 226 | 227 | [HalBaru-sepertinyatidakterpakai] 228 | say=baiklah... saya coba memahami dulu tentang %word% 229 | say=hal baru untuk saya.\nsaya akan simpan dulu %word% di perbendaharaan saya. 230 | 231 | [Cari] 232 | say=Cari tentang apa yaa? 233 | say=Cari apa? 234 | 235 | [PerintahSaja] 236 | say=apa yaa? 237 | say=maaf, saya belum paham. 238 | 239 | [EmailTidakValid] 240 | say=Maaf, sepertinya email anda tidak valid 241 | 242 | [ResponBaik] 243 | say=baiklah 244 | say=syukurlah ... 245 | say=senang mendengarnya 246 | say=terima kasih 247 | 248 | [ResponBuruk] 249 | say=hhmm.. 250 | say=Semoga akan terus membaik hasilnya 251 | say=Sedih merasakannya 252 | say=Seandainya kamu bisa merasakan gerimisnya hati ini 253 | say=Sayang sekali 254 | say=Sayang sekali, bagaimana kalau diusahakan lagi 255 | say=Mohon maaf jika belum sesuai dengan harapan 256 | 257 | [UngkapanBaik] 258 | say=hhmmm.... 259 | say=berharap bisa memberikan sesuatu yg lebih baik lagi 260 | say=dicoba untuk berusaha lebih baik lagi 261 | say=terbaik yang bisa dilakukan 262 | say=terus berusaha yang terbaik 263 | 264 | [UngkapanBuruk] 265 | say=Maaf .. 266 | say=berharap bisa memberikan sesuatu yg lebih baik lagi 267 | say=dicoba untuk berusaha lebih baik lagi 268 | say=terbaik yang bisa dilakukan 269 | say=terus berusaha yang terbaik 270 | 271 | [InginTahu] 272 | say=mmm.. boleh tau apa itu %word% ? 273 | say=%word% ... apa itu? 274 | say=saya belum ada perbendaharaan kata %word%, bisa dijelaskan? 275 | say=tolong jelasin dong apa itu %word% 276 | 277 | [InginTanya] 278 | say=yaa... ada yg bisa saya bantu? 279 | say=bagaimana? 280 | say=silahkan, dengan senang hati 281 | say=boleh 282 | 283 | [TidakYakin] 284 | say=Saya berusaha menyampaikan hal yang saya tahu saja 285 | say=Saya tidak tahu harus mengatakan apa lagi 286 | say=Sungguh 287 | say=Sepertinya demikian 288 | say=Sepengetahuan saya begitu 289 | 290 | [TanyaSeandainya] 291 | say=saya coba pikir-pikir dulu 292 | say=saya kurang paham 293 | say=mmmmhh.... gimana yaa... 294 | say=sepertinya belum memungkinkan 295 | say=bagaimana kalau sebaliknya saja? 296 | say=agak sulit juga yaa... 297 | 298 | [KataTanyaSaja] 299 | say=apa? 300 | say=apa yaa? 301 | say=bagaimana? 302 | say=%Tanya_value% apanya? 303 | say=Tentang apa? 304 | 305 | [MintaTolong] 306 | say=bagaimana? 307 | say=apa yang bisa saya bantu? 308 | say=ada yg bisa dibantu? 309 | say=bagaimana? 310 | 311 | [TelegramBotStart] 312 | say=Hi, Selamat %time_session%.\nSelamat datang di layanan ChatBot kami.\nApa kabar? 313 | 314 | [Larangan] 315 | say=Oke 316 | say=Saya usahkan 317 | say=Baiklah 318 | say=mmmm... duhh.. saya usahakan yaa... 319 | 320 | [ResiPaket] 321 | say=Mohon ditunggu, saya cari dahulu .. 322 | say=Tunggu sebentar .. 323 | say=bentar, saya cek dulu 324 | 325 | [xxx] 326 | say=xxxxxx 327 | 328 | [SuggestionResponse] 329 | say=sarannya kami simpan, terima kasih. 330 | say=Terima kasih masukannya 331 | 332 | [CarikStart] 333 | say=tunggu sebentar ... 334 | say=... bentar yaa ... 335 | say=siap-siap dulu .. 336 | 337 | [CarikStop] 338 | say=Oke, siippp... 339 | say=Yak 340 | say=Siap 341 | 342 | [Lahir] 343 | say=belum lama 344 | say=baru-baru saja siihh... 345 | say=kurang tau juga 346 | say=mungkin anda malah lebih tahu 347 | 348 | [NoEnglish] 349 | say=no i cannot 350 | say=of course, i cannot 351 | 352 | [CariJodoh] 353 | say=Yang bagaimana? 354 | say=MMmmm... Sebaiknya bukan dengan saya menyampaikannya 355 | say=Sebaiknya anda bergaul dengan manusia, bukan dengan bot seperti saya 356 | say=Sulit juga 357 | 358 | [CariJodohKriteria] 359 | say=Sepertinya ada 360 | say=Ada sihh... tapi susah juga sepertinya 361 | say=Bukannya banyak di sekitar Anda ? 362 | 363 | [TanyaPasanganSeseorang] 364 | say=Saya belum kenal 365 | say=Kurang tau juga 366 | say=Oohh... sudah punya yaaa.. 367 | say=Saya cari tahu dulu yaa... 368 | 369 | [Nikah] 370 | say=Kalau sudah ada calonnya 371 | say=Kalau sudah ada jodohnya 372 | say=dia sudah yakin? 373 | say=Mesti pikir-pikir dulu 374 | 375 | [Lulus] 376 | say=Kalau sudah waktunya 377 | say=Kurang tahu juga 378 | say=Kurang ingat 379 | say=Saya kurang yakin 380 | 381 | [Kencan] 382 | say=Apa bisa? 383 | say=Yakin? 384 | 385 | [HalTerlarang] 386 | say=Maaf, kami tidak membicarakan hal tersebut di sini 387 | say=Sebaiknya tidak 388 | 389 | [KeadaanBaik] 390 | say=Syukurlah 391 | say=Selalu semangat 392 | say=Semangat selalu 393 | 394 | [KeadaanBuruk] 395 | say=Mesti semangat 396 | say=Harus semangat selalu 397 | say=Harus jaga kondisi selalu 398 | say=Jaga kesehatan 399 | say=jaga diri baik2 400 | say=jaga kesehatanmu 401 | say=semangat yaa 402 | say=mesti semangat 403 | 404 | 405 | [Menghibur] 406 | say=iya, terima kasih 407 | say=tetep semangat kok 408 | say=masih berusaha yang terbaik 409 | 410 | [TidakPunyaSesuatu] 411 | say=Sebaiknya segera dipunyai 412 | say=Sayang sekali 413 | say=Anda lebih tau kebutuhan anda sendiri 414 | 415 | [EmailBuat] 416 | say=Maaf, saya belum bisa 417 | say=Maaf, coba hubungi technical support anda saja 418 | say=Mohon maaf, belum bisa 419 | say=Sayang sekali belum bisa membantu Anda 420 | 421 | [MakanBuat] 422 | say=Maaf, saya belum bisa 423 | say=Mohon maaf, belum bisa 424 | say=Sayang sekali belum bisa membantu Anda 425 | 426 | [MakanBeli] 427 | say=Maaf, saya belum bisa 428 | say=Mohon maaf, belum bisa 429 | say=Sayang sekali belum bisa membantu Anda 430 | say=Sebaiknya anda pesan melalui jasa layanan yang sudah ada. 431 | say=Maaf, belum bisa melayani pembelian makanan 432 | 433 | [PulsaBeli] 434 | say=Maaf, saya belum bisa 435 | say=Mohon maaf, belum bisa 436 | say=Sayang sekali belum bisa membantu Anda 437 | say=Sebaiknya anda pesan melalui jasa layanan yang sudah ada. 438 | say=Maaf, belum bisa melayani pembelian pulsa 439 | 440 | [PembantuCari] 441 | say=cari pembantu yaa? 442 | 443 | [LoremIpsum] 444 | say=seperti biasa: Lorem ipsum dolor sit amet, consectetur adipiscing elit. De quibus cupio scire quid sentias. Parvi enim primo ortu sic iacent, tamquam omnino sine animo sint. Cupiditates non Epicuri divisione finiebat, sed sua satietate. Duo Reges: constructio interrete. Explanetur igitur. Sumenda potius quam expetenda. 445 | say=jawaban standard: Lorem ipsum dolor sit amet, consectetur adipiscing elit. De quibus cupio scire quid sentias. Parvi enim primo ortu sic iacent, tamquam omnino sine animo sint. Cupiditates non Epicuri divisione finiebat, sed sua satietate. Duo Reges: constructio interrete. Explanetur igitur. Sumenda potius quam expetenda. 446 | say=anda sudah pasti tau jawabannya apa 447 | 448 | [Hadir] 449 | say=yaa.. hadir 450 | say=hai, salam jumpa 451 | say=iya.. apa kabar... 452 | say=hehehheee... 453 | 454 | [telolet] 455 | say=telotelotelotelooooooleeettt... 456 | say=teeeetttt.... 457 | say=telolet telolet let let let 458 | 459 | [PropertyWithDetail] 460 | say=asdad 461 | 462 | -------------------------------------------------------------------------------- /source/common/direct_handler.pas: -------------------------------------------------------------------------------- 1 | unit direct_handler; 2 | 3 | {$mode objfpc}{$H+} 4 | {___$ModeSwitch UnicodeStrings} 5 | { $codepage cp1252} 6 | {$codepage UTF8} 7 | {$DEFINE INTERNAL_CARIK__} 8 | 9 | //pertanyaan atau perintah 10 | 11 | interface 12 | 13 | uses 14 | StrUtils, 15 | kamuskemdikbud_integration, 16 | elasticsearch_integration, 17 | carik_webmodule, 18 | fpjson, RegExpr, googlegeocoding_integration, 19 | carik_controller, simplebot_controller, logutil_lib, 20 | clarifai_integration, telegram_integration, googleplacesearch_integration, 21 | Classes, SysUtils, fpcgi, HTTPDefs, fastplaz_handler, database_lib, 22 | json_helpers, string_helpers, datetime_helpers, array_helpers; 23 | 24 | const 25 | BOTNAME_DEFAULT = 'Carik'; 26 | 27 | type 28 | 29 | { TCarikHandler } 30 | 31 | TCarikHandler = class(TCarikWebModule) 32 | private 33 | FOnMessage: TOnMessageEvent; 34 | forceRespond: boolean; 35 | jsonData: TJSONData; 36 | 37 | procedure BeforeRequestHandler(Sender: TObject; ARequest: TRequest); 38 | public 39 | constructor CreateNew(AOwner: TComponent; CreateMode: integer); override; 40 | destructor Destroy; override; 41 | 42 | procedure Get; override; 43 | procedure Post; override; 44 | procedure Put; override; 45 | procedure Options; override; 46 | 47 | function OnErrorHandler(const Message: string): string; 48 | Property OnMessage : TOnMessageEvent Read FOnMessage Write FOnMessage; 49 | end; 50 | 51 | implementation 52 | 53 | uses json_lib, common; 54 | 55 | constructor TCarikHandler.CreateNew(AOwner: TComponent; CreateMode: integer); 56 | begin 57 | inherited CreateNew(AOwner, CreateMode); 58 | BeforeRequest := @BeforeRequestHandler; 59 | 60 | Carik := TCarikController.Create; 61 | end; 62 | 63 | destructor TCarikHandler.Destroy; 64 | begin 65 | Carik.Free; 66 | inherited Destroy; 67 | end; 68 | 69 | 70 | // Init First 71 | procedure TCarikHandler.BeforeRequestHandler(Sender: TObject; ARequest: TRequest); 72 | begin 73 | Response.ContentType := 'application/json'; 74 | end; 75 | 76 | // GET Method Handler 77 | procedure TCarikHandler.Get; 78 | begin 79 | OutputJson(0, 'Invalid Method'); 80 | end; 81 | 82 | // POST Method Handler 83 | // CURL example: 84 | // curl "http://local-carik.fastplaz.com/ai/" -X POST -d '{"message":{"message_id":0,"chat":{"id":0},"text":"Hi"}}' 85 | procedure TCarikHandler.Post; 86 | var 87 | s, text_response, responseFormat: string; 88 | chatID, chatType, _userID, fullName, userName, groupID, groupName: string; 89 | i, j: integer; 90 | json: TJSONUtil; 91 | cmdAction, parameterAction, fieldAction : TStrings; 92 | isHandled: Boolean; 93 | replyText: TStringList; 94 | begin 95 | Response.Content := '{}'; 96 | forceRespond := False; 97 | BOLD_CODE := '**'; 98 | ITALIC_CODE := '*'; 99 | responseFormat := ''; 100 | Text := ''; 101 | 102 | // telegram style 103 | // {"message":{"message_id":0,"text":"Hi","chat":{"id":0}}} 104 | try 105 | jsonData := GetJSON(Request.Content); 106 | try 107 | Text := jsonData.GetPath('message.text').AsString; 108 | except 109 | end; 110 | //Text := jsonData.Value['message/text']; 111 | if Text = 'False' then 112 | Text := ''; 113 | 114 | messageID := jsonData.Value['message/message_id']; 115 | chatID := jsonData.Value['message/chat/id']; 116 | chatType := jsonData.Value['message/chat/type']; 117 | groupID := jsonData.Value['message/chat/group_id']; 118 | groupName := jsonData.Value['message/chat/group_name']; 119 | 120 | _userID := jsonData.Value['message/from/id']; 121 | userName := jsonData.Value['message/from/username']; 122 | if userName = '' then 123 | userName := trim(jsonData.Value['message/from/name']); 124 | fullName := trim( jsonData.Value['message/from/first_name'] + ' ' 125 | + jsonData.Value['message/from/last_name']); 126 | if fullName = '' then 127 | fullName := trim(jsonData.Value['message/from/name']); 128 | if fullName = '' then 129 | fullName := userName; 130 | responseFormat := jsonData.Value['message/format']; 131 | DashboardDeviceID := s2i(jsonData.Value['message/chat/dashboard_device_id']); 132 | IsDelayReplay := s2b(jsonData.Value['delay_reply']); 133 | except 134 | end; 135 | 136 | try 137 | DashboardDeviceID := s2i(jsonData.Value['message/chat/dashboard_device_id']); 138 | except 139 | end; 140 | s := trim(_GET['device_id']); 141 | if s.IsNotEmpty then DashboardDeviceID := s2i(s);; 142 | 143 | 144 | //if ClientId = '263' then LogUtil.Add(Request.Content, 'lll'); 145 | 146 | try 147 | MessageType := jsonData.Value['message/chat/type']; 148 | replyFromMessageID := jsonData.Value['message/reply/message_id']; 149 | if replyFromMessageID.IsNotEmpty then 150 | begin 151 | isReplyMessage := True; 152 | replyFromUserID := jsonData.Value['message/reply/user_id']; 153 | replyFromFullName := jsonData.Value['message/reply/full_name']; 154 | replyFromText := jsonData.Value['message/reply/text']; 155 | 156 | SimpleBOT.AdditionalParameters.Values['reply_from_message_id'] := replyFromMessageID; 157 | SimpleBOT.AdditionalParameters.Values['reply_from_user_id'] := replyFromUserID; 158 | SimpleBOT.AdditionalParameters.Values['reply_from_fullname'] := replyFromFullName; 159 | SimpleBOT.AdditionalParameters.Values['reply_from_text'] := replyFromText; 160 | end; 161 | except 162 | end; 163 | 164 | if MessageType.IsEqualTo('image') then 165 | begin 166 | try 167 | FileList := TJSONArray(jsonData.GetPath('message').GetPath('files')); 168 | except 169 | end; 170 | end; 171 | 172 | // maybe submitted from post data 173 | //if Text = '' then 174 | // Text := _POST['text']; 175 | 176 | ChannelId := _GET['channel']; 177 | if ChannelId.IsEmpty then 178 | begin 179 | ChannelId := Request.QueryString; 180 | //todo: remove after mobile app fixed 181 | {$IFDEF INTERNAL_CARIK} 182 | if not ChannelId.IsExists('channel=android') then Exit; 183 | {$ENDIF} 184 | ChannelId := '';///TODO: 185 | end; 186 | if ChannelId = 'm' then 187 | ChannelId := 'android'; 188 | if ChannelId = 'an' then 189 | ChannelId := 'android'; 190 | if ChannelId = 'and' then 191 | ChannelId := 'android'; 192 | if ChannelId = 'whatsapp' then 193 | MessengerMode := mmWhatsapp; 194 | if ChannelId = 'discord' then 195 | MessengerMode := mmDiscord; 196 | 197 | // CarikBOT isRecording 198 | Carik.UserPrefix := ''; 199 | Carik.UserID := chatID; 200 | Carik.UserID := _userID; //! 201 | Carik.UserName := userName; 202 | Carik.FullName := fullName; 203 | 204 | SessionController.SessionPrefix := 'carik'; 205 | SessionController.SessionSuffix := chatID; 206 | SessionController.ForceUniqueID := chatID; 207 | SessionController.StartSession; 208 | 209 | SimpleBOT.SessionUserID := UniqueID; 210 | SimpleBOT.FirstSessionResponse := s2b(Config[CONFIG_FIRST_SESSION_RESPONSE]); 211 | 212 | try 213 | Carik.GroupName := jsonData.GetPath('message.chat.title').AsString; 214 | except 215 | end; 216 | Carik.UserPrefix := channelID; 217 | 218 | if IsGlobalUserBlackListed(PrefixId + '-' + Carik.UserID) then 219 | begin 220 | LogUtil.Add('user blacklist: ' + PrefixId + '-' + Carik.UserID + '|' + Carik.FullName,'TELE'); 221 | Response.Content := '{"status":"'+Carik.UserID+' blaclisted"}'; 222 | Exit; 223 | end; 224 | 225 | // remove mention from text 226 | OriginalText := Text.Trim; 227 | Text := Text.ToLower; 228 | { 229 | if Pos('@' + BOTNAME_DEFAULT, Text) = 1 then 230 | begin 231 | Text := StringReplace(Text, '@' + BOTNAME_DEFAULT + 'Bot', '', [rfReplaceAll, rfIgnoreCase]); 232 | end; 233 | s := '@' + Config[_AI_CONFIG_NAME] + 'bot'; 234 | s := LowerCase(s); 235 | if Pos(s, Text) = 1 then 236 | Text := StringReplace(Text, s, '', [rfReplaceAll, rfIgnoreCase]); 237 | } 238 | //Text := StringReplace(Text, '@' + BOTNAME_DEFAULT + 'Bot', '', 239 | // [rfReplaceAll, rfIgnoreCase]); 240 | 241 | Text := Text.Replace('@+62811857001',''); //ulil 242 | Text := Text.Replace('@62811857001',''); //ulil 243 | Text := Text.Replace('@' + BOTNAME_DEFAULT + 'Bot',''); 244 | Text := Text.Replace('@' + BOTNAME_DEFAULT + ' Bot',''); 245 | Text := Text.Replace('@' + BOTNAME_DEFAULT,''); 246 | Text := Text.Replace(BOTNAME_DEFAULT + 'Bot',''); 247 | 248 | Text := Trim(Text); 249 | if Text = '' then 250 | Exit; 251 | 252 | // Main AI BOT 253 | //SimpleBOT := TSimpleBotModule.Create; 254 | //if BotName.IsNotEmpty then 255 | // SimpleBOT.BotName := BotName; 256 | //SimpleBOT.TrimMessage := True; 257 | 258 | // TODO: REMOVE - force 259 | //SimpleBOT.FirstSessionResponse := False; 260 | //SimpleBOT.SecondSessionResponse := True; 261 | 262 | SimpleBOT.chatID := chatID; 263 | if userName <> '' then 264 | begin 265 | try 266 | SimpleBOT.UserData['Name'] := userName; 267 | SimpleBOT.UserData['FullName'] := fullName; 268 | except 269 | end; 270 | end; 271 | 272 | s := jsonData.Value['message/chat/is_group']; 273 | Carik.IsGroup := s2b(s); 274 | 275 | if groupID.IsEmpty then 276 | groupID := _GET['groupID']; 277 | if not groupID.IsEmpty then 278 | begin 279 | chatID := groupID; 280 | Carik.GroupChatID := groupID; 281 | SimpleBOT.AdditionalParameters.Values['group_id'] := groupID; 282 | SimpleBOT.AdditionalParameters.Values['GroupID'] := groupID; 283 | if groupName.IsNotEmpty then 284 | begin 285 | SimpleBOT.AdditionalParameters.Values['group_name'] := groupName; 286 | SimpleBOT.AdditionalParameters.Values['GroupName'] := groupName; 287 | end; 288 | end; 289 | SimpleBOT.AdditionalParameters.Values['FullName'] := fullName; 290 | SimpleBOT.AdditionalParameters.Values['full_name'] := fullName; 291 | if IsDebug then 292 | begin 293 | SimpleBOT.AdditionalParameters.Values['ClientID'] := Config[CONFIG_CLIENT_ID]; 294 | end; 295 | 296 | 297 | // check if any custom handler 298 | if Assigned(FOnMessage) then 299 | begin 300 | isHandled := False; 301 | replyText := TStringList.Create; 302 | replyText.Text := FOnMessage(OriginalText, isHandled); 303 | for j:=0 to SimpleBOT.AdditionalParameters.Count-1 do 304 | begin 305 | s := SimpleBOT.AdditionalParameters.Names[j]; 306 | SimpleBOT.SimpleAI.Parameters.Values[s] := SimpleBOT.AdditionalParameters.ValueFromIndex[j]; //manual add parameter 307 | end; 308 | end; 309 | 310 | 311 | if FormInputHandler() then 312 | begin 313 | isHandled := True; 314 | end; 315 | 316 | if not isHandled then 317 | Text := GenerateTextFromCustomActionOption(Text); 318 | if IsMuted then 319 | begin 320 | //LogUtil.Add(SimpleBOT.SimpleAI.ResponseJson, 'mute'); 321 | LogChatPayload.Text:= Response.Content; 322 | LogChat(ChannelId, Carik.GroupChatID, Carik.GroupName, Carik.UserID, Carik.UserName, Carik.FullName, OriginalText, '', Carik.IsGroup, True); 323 | //OutputJson(11, 'muted: ' + MutedUntil.AsString); 324 | Response.Content:= SimpleBOT.SimpleAI.ResponseJson; 325 | Exit; 326 | end; 327 | 328 | //Text := Text.Replace(',',''); //koma 329 | if not isHandled then 330 | begin 331 | BotInit; 332 | GPTTimeout := GPT_TIMEOUT_DEFAULT; 333 | Response.Content := ProcessText(Text); 334 | SimpleBOT.SimpleAI.ResponseText.Text := Prefix + RemoveDummyImageLink(SimpleBOT.SimpleAI.ResponseText.Text).Trim; 335 | SimpleBOT.SimpleAI.ResponseText.Text := preg_replace('\*\*(.*?)\*\*', '*$1*', SimpleBOT.SimpleAI.ResponseText.Text); 336 | if responseFormat = 'text' then 337 | begin 338 | SimpleBOT.SimpleAI.ResponseText.Text := RemoveMarkDown(SimpleBOT.SimpleAI.ResponseText.Text); 339 | end; 340 | // if oTTo: telegram, instagram 341 | if (ChannelId = '52') or (ChannelId = '60') then 342 | begin 343 | // remove markdown 344 | s := (SimpleBOT.SimpleAI.ResponseText.Text); 345 | s := preg_replace('\*(.*?)\*', '$1', s); 346 | s := preg_replace('\[(.*?)\]\((.*?)\)', '$1, $2', s); // url 347 | SimpleBOT.SimpleAI.ResponseText.Text := s; 348 | end; 349 | // if oTTo: wa, bisnis 350 | if (ChannelId = '61') or (ChannelId = '62') then 351 | begin 352 | s := (SimpleBOT.SimpleAI.ResponseText.Text); 353 | s := preg_replace('\*\*(.*?)\*\*', '*$1*', s); // bold* 354 | s := preg_replace('\[(.*?)\]\((.*?)\)', '$1, $2', s); // url 355 | SimpleBOT.SimpleAI.ResponseText.Text := s; 356 | end; 357 | end else begin 358 | SimpleBOT.SimpleAI.ResponseText.Text := replyText.Text; 359 | replyText.Free 360 | end; 361 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 362 | 363 | if not SimpleBOT.IsExternal then 364 | begin 365 | if SimpleBOT.SimpleAI.IntentName <> 'Waktu' then 366 | begin 367 | //ulil 368 | s := 'http://global-tts.carik.id/speech/generate/' + UrlEncode(SimpleBOT.SimpleAI.ResponseText.Text); 369 | //s := file_get_contents( s); //ulil 370 | end; 371 | end; 372 | 373 | //Exec Command 374 | { 375 | if Carik.IsCommand(SimpleBOT.SimpleAI.ResponseText.Text) then 376 | begin 377 | SimpleBOT.SimpleAI.ResponseText.Text := 378 | Carik.ExecCommand(SimpleBOT.SimpleAI.ResponseText.Text); 379 | if SimpleBOT.SimpleAI.ResponseText.Text = '' then 380 | SimpleBOT.SimpleAI.ResponseText.Text := 381 | SimpleBOT.GetResponse('DataTidakAdaResponse'); 382 | //TODO: generate user data and object 383 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 384 | end; 385 | } 386 | 387 | if IsCommand(SimpleBOT.SimpleAI.ResponseText.Text) then 388 | begin 389 | SimpleBOT.SimpleAI.ResponseText.Text := 390 | ExecCommand(SimpleBOT.SimpleAI.ResponseText.Text); 391 | if SimpleBOT.SimpleAI.ResponseText.Text = '' then 392 | SimpleBOT.SimpleAI.ResponseText.Text := 393 | SimpleBOT.GetResponse('DataTidakAdaResponse'); 394 | //TODO: generate user data and object 395 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 396 | end; 397 | 398 | { 399 | if not Prefix.IsEmpty then 400 | begin 401 | SimpleBOT.SimpleAI.ResponseText[0] := Prefix + SimpleBOT.SimpleAI.ResponseText[0]; 402 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 403 | end; 404 | } 405 | if Prefix.IsNotEmpty then 406 | begin 407 | if HideTextReply then 408 | begin 409 | SimpleBOT.SimpleAI.ResponseText.Text := Prefix; 410 | Prefix := ''; 411 | end; 412 | end; 413 | 414 | if Suffix.IsNotEmpty then 415 | begin 416 | if GenericContent then 417 | begin 418 | if SimpleBOT.SimpleAI.ResponseText.Count = 0 then 419 | SimpleBOT.SimpleAI.ResponseText.Add(Suffix) 420 | else 421 | begin 422 | j := SimpleBOT.SimpleAI.ResponseText.Count-1; 423 | SimpleBOT.SimpleAI.ResponseText[j] := SimpleBOT.SimpleAI.ResponseText[j] + Suffix; 424 | end; 425 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 426 | end; 427 | end; 428 | 429 | // custom action: button, quickreply 430 | if IsCustomAction then 431 | begin 432 | SaveActionToUserData(CustomReplyType, CustomReplyData.Data); 433 | if not CustomActionAsText.IsEmpty then 434 | begin 435 | SimpleBOT.SimpleAI.ResponseText.Text := SimpleBOT.SimpleAI.ResponseText.Text.Trim 436 | + '\n' + ACTION_CAPTION + '\n' + CustomActionAsText.Replace(#10,'\n'); 437 | if CustomActionSuffix.IsNotEmpty then 438 | SimpleBOT.SimpleAI.ResponseText.Text := SimpleBOT.SimpleAI.ResponseText.Text.Trim 439 | + '\n' + CustomActionSuffix.Replace(#10,'\n'); 440 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 441 | end; 442 | end; 443 | Response.Content := GenerateResponseJson; 444 | 445 | if ActionCallback <> '' then 446 | begin 447 | parameterAction := Explode(ActionCallback, '|'); 448 | cmdAction := Explode(parameterAction[0], '.'); 449 | 450 | json := TJSONUtil.Create; 451 | json.LoadFromJsonString( Response.Content, False); 452 | json['response/action/callback_string'] := ActionCallback; 453 | json['response/action/callback_name'] := cmdAction[0]; 454 | if cmdAction.Count > 1 then 455 | json['response/action/callback_method'] := cmdAction[1]; 456 | for i := 1 to parameterAction.count - 1 do 457 | begin 458 | fieldAction := Explode(parameterAction[i], '='); 459 | json['response/action/parameter_' + i2s(i)] := parameterAction[i]; 460 | try 461 | json['response/action/' + fieldAction[0]] := fieldAction[1]; 462 | except 463 | end; 464 | fieldAction.Free; 465 | end; 466 | 467 | //json['processing_time'] := ProcessingTime; 468 | //if SimpleBOT.SimpleAI.ElapsedTime > 0 then 469 | //begin 470 | // json['processing_time'] := SimpleBOT.SimpleAI.ElapsedTime.ToString; 471 | //end; 472 | Response.Content := json.AsJSONFormated; 473 | end; 474 | 475 | if Assigned(ElementArray) then 476 | begin 477 | json := TJSONUtil.Create; 478 | json.LoadFromJsonString( Response.Content, False); 479 | 480 | //json.ValueArray['response/action/data'] := ElementArray; 481 | Response.Content := json.AsJSONFormated; 482 | json.Free; 483 | end; 484 | 485 | //--- 486 | 487 | text_response := SimpleBOT.SimpleAI.ResponseText.Text; 488 | json := TJSONUtil.Create; 489 | json.LoadFromJsonString( SimpleBOT.SimpleAI.ResponseJson, False); 490 | s := json['response/action/callback_string']; 491 | if s <> '' then 492 | begin 493 | //text_response := '#internalAction'; 494 | end; 495 | json.Free; 496 | 497 | 498 | if not (_GET['_DEBUG'] = '1') then 499 | begin 500 | if channelID = 'direct' then 501 | channelID := DEFAULT_CHANNEL_ID; 502 | if channelID = 'android' then 503 | channelID := ANDROID_CHANNEL_ID; 504 | if channelID = 'i' then 505 | channelID := IOS_CHANNEL_ID; 506 | if channelID = 'ios' then 507 | channelID := IOS_CHANNEL_ID; 508 | //if channelID = 'whatsapp' then 509 | // channelID := WHATSAPP_CHANNEL_ID; 510 | if channelID = 'instagram' then 511 | channelID := INSTAGRAM_CHANNEL_ID; 512 | if channelID = 'telegram_userbot' then 513 | channelID := TELEGRAM_USERBOT_CHANNEL_ID; 514 | Analytics(ChannelId, SimpleBOT.SimpleAI.IntentName, Text, channelID + '-' + Carik.UserID); 515 | if (_GET['_NOLOG'] = '') then 516 | begin 517 | LogChatPayload.Text:= Response.Content; 518 | LogChat(ChannelId, Carik.GroupChatID, Carik.GroupName, Carik.UserID, Carik.UserName, Carik.FullName, OriginalText, text_response, Carik.IsGroup, True); 519 | end; 520 | end; 521 | 522 | SimpleBOT.Free; 523 | Response.ContentType := 'application/json'; 524 | end; 525 | 526 | procedure TCarikHandler.Put; 527 | begin 528 | inherited Put; 529 | end; 530 | 531 | procedure TCarikHandler.Options; 532 | begin 533 | Response.Content := '{}'; 534 | end; 535 | 536 | 537 | 538 | function TCarikHandler.OnErrorHandler(const Message: string): string; 539 | var 540 | s: string; 541 | begin 542 | s := Trim(Message); 543 | s := StringReplace(SimpleBOT.GetResponse('InginTahu', ''), '%word%', 544 | s, [rfReplaceAll]); 545 | Result := s; 546 | 547 | 548 | // simpan message ke DB, untuk dipelajari oleh AI 549 | 550 | end; 551 | 552 | 553 | 554 | end. 555 | -------------------------------------------------------------------------------- /source/common/facebook_handler.pas: -------------------------------------------------------------------------------- 1 | unit facebook_handler; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | interface 6 | 7 | uses 8 | {$if FPC_FULlVERSION >= 30200} 9 | opensslsockets, 10 | {$endif} 11 | carik_webmodule, logutil_lib, simplebot_controller, carik_controller, 12 | facebookmessenger_integration, witai_integration, json_lib, 13 | fpjson, process, 14 | Classes, SysUtils, fpcgi, HTTPDefs, fastplaz_handler, database_lib, 15 | string_helpers, json_helpers; 16 | 17 | {$include ../common/carik.inc} 18 | _DEVELOPMENT_ = False; 19 | 20 | type 21 | 22 | { TFacebookHandler } 23 | 24 | TFacebookHandler = class(TCarikWebModule) 25 | private 26 | FOnMessage: TOnMessageEvent; 27 | FOnSpam: TOnSpamEvent; 28 | Facebook: TFacebookMessengerIntegration; 29 | procedure BeforeRequestHandler(Sender: TObject; ARequest: TRequest); 30 | 31 | // Payload 32 | function payloadTestHandler(const APayload, ATitle: string): string; 33 | function payloadTextHandler(const APayload, ATitle: string): string; 34 | function isPayloadCommand(const AText: string): boolean; 35 | 36 | function sendButton(ACaption: string; ADataAsJson: TJSONUtil): boolean; 37 | function generateQuickReplay: boolean; 38 | 39 | public 40 | constructor CreateNew(AOwner: TComponent; CreateMode: integer); override; 41 | destructor Destroy; override; 42 | 43 | procedure Get; override; 44 | procedure Post; override; 45 | 46 | Property OnMessage : TOnMessageEvent Read FOnMessage Write FOnMessage; 47 | Property OnSpam : TOnSpamEvent Read FOnSpam Write FOnSpam; 48 | end; 49 | 50 | implementation 51 | 52 | uses common; 53 | 54 | constructor TFacebookHandler.CreateNew(AOwner: TComponent; CreateMode: integer); 55 | begin 56 | inherited CreateNew(AOwner, CreateMode); 57 | BeforeRequest := @BeforeRequestHandler; 58 | Facebook := TFacebookMessengerIntegration.Create; 59 | Facebook.BotName := BotName; 60 | Facebook.Token := Config[FACEBOOK_TOKEN]; 61 | if Token.IsNotEmpty then 62 | Facebook.Token := Token; 63 | 64 | end; 65 | 66 | destructor TFacebookHandler.Destroy; 67 | begin 68 | inherited Destroy; 69 | end; 70 | 71 | // Init First 72 | procedure TFacebookHandler.BeforeRequestHandler(Sender: TObject; ARequest: TRequest); 73 | begin 74 | //Response.ContentType := 'application/json'; 75 | end; 76 | 77 | function TFacebookHandler.payloadTestHandler(const APayload, ATitle: string): string; 78 | begin 79 | Result := 'echo: ' + ATitle; 80 | end; 81 | 82 | function TFacebookHandler.payloadTextHandler(const APayload, ATitle: string): string; 83 | var 84 | payloadText: string; 85 | lst: TStrings; 86 | begin 87 | payloadText := ATitle; 88 | lst := Explode(APayload, '&'); 89 | if lst.Count > 1 then 90 | payloadText := lst.Values['text']; 91 | Result := payloadText; 92 | end; 93 | 94 | function TFacebookHandler.isPayloadCommand(const AText: string): boolean; 95 | begin 96 | Result := AText.IsExists('|'); 97 | end; 98 | 99 | function TFacebookHandler.sendButton(ACaption: string; ADataAsJson: TJSONUtil 100 | ): boolean; 101 | var 102 | indexItem: integer; 103 | buttonList: TJSONArray; 104 | buttonData: TJSONArray; 105 | 106 | procedure _generateButtonList(AData: TJSONArray; var Output: TJSONArray); 107 | var 108 | rowIndex, itemIndex: integer; 109 | s, url, size, callbackData: string; 110 | sourceRowData: TJSONUtil; 111 | buttonData: TJSONObject; 112 | lst: TStrings; 113 | begin 114 | if AData.Count = 0 then 115 | Exit; 116 | sourceRowData := TJSONUtil.Create; 117 | for rowIndex := 0 to AData.Count - 1 do 118 | begin 119 | sourceRowData.LoadFromJsonString(AData.Items[rowIndex].AsJSON, False); 120 | for itemIndex := 0 to TJSONArray(sourceRowData.Data).Count - 1 do 121 | begin 122 | s := TJSONArray(sourceRowData.Data).Items[itemIndex].ValueOfNameAsString('text'); 123 | callbackData := TJSONArray(sourceRowData.Data).Items[itemIndex].ValueOfNameAsString('callback_data'); 124 | url := TJSONArray(sourceRowData.Data).Items[itemIndex].ValueOfNameAsString('url'); 125 | try 126 | size := 'full'; 127 | size := TJSONArray(sourceRowData.Data).Items[itemIndex].ValueOfNameAsString('size'); 128 | if size.IsEmpty then size := 'full'; 129 | except 130 | end; 131 | 132 | buttonData := TJSONObject.Create; 133 | buttonData.Add('title', s); 134 | 135 | // url 136 | if not url.IsEmpty then 137 | begin 138 | buttonData.Add('type', 'web_url'); 139 | buttonData.Add('url', url); 140 | buttonData.Add('webview_share_button', 'hide'); 141 | buttonData.Add('webview_height_ratio', size); 142 | end; 143 | 144 | // callback data 145 | if not callbackData.IsEmpty then 146 | begin 147 | lst := Explode(callbackData, '&'); 148 | if not lst.Values['text'].IsEmpty then 149 | begin 150 | buttonData.Add('type', 'postback'); 151 | buttonData.Add('payload', 'text='+lst.Values['text'].Trim); 152 | end; 153 | end; 154 | 155 | Output.Add(buttonData); 156 | end; 157 | 158 | end; 159 | sourceRowData.Free; 160 | end; 161 | 162 | begin 163 | Result := False; 164 | 165 | if ADataAsJson.Data.Count = 0 then 166 | Exit; 167 | 168 | ACaption := ACaption.Replace('\n', #10); 169 | 170 | buttonList := TJSONArray.Create; 171 | _generateButtonList(TJSONArray(ADataAsJson.Data), buttonList); 172 | 173 | buttonData := TJSONArray.Create; 174 | for indexItem := 0 to buttonList.Count - 1 do 175 | begin 176 | buttonData.Add(buttonList.Items[indexItem]); 177 | //die('o:'+buttonData.AsJSON);exit; 178 | 179 | if ((indexItem+1)mod 3) = 0 then 180 | begin 181 | Facebook.SendButton(Facebook.UserID, ACaption, buttonData); 182 | buttonData.Clear; 183 | ACaption := '»'; 184 | end; 185 | end; 186 | if buttonData.Count > 0 then 187 | begin 188 | Facebook.SendButton(Facebook.UserID, ACaption, buttonData); 189 | end; 190 | buttonData.Free; 191 | Result := True; 192 | end; 193 | 194 | function TFacebookHandler.generateQuickReplay: boolean; 195 | var 196 | rowIndex, itemIndex: integer; 197 | s, title, callbackData, image: string; 198 | sendAsButton: boolean; 199 | begin 200 | Result := False; 201 | for rowIndex := 0 to CustomReplyData.Data.Count-1 do 202 | begin 203 | for itemIndex:=0 to CustomReplyData.Data.Items[rowIndex].Count-1 do 204 | begin 205 | sendAsButton := True; 206 | title := CustomReplyData.Data.Items[rowIndex].Items[itemIndex].Value['text']; 207 | callbackData := CustomReplyData.Data.Items[rowIndex].Items[itemIndex].Value['callback_data']; 208 | image := CustomReplyData.Data.Items[rowIndex].Items[itemIndex].Value['image']; 209 | if image.IsEmpty then 210 | image := QUICK_REPLY_IMAGE_DEFAULT; 211 | 212 | s := CustomReplyData.Data.Items[rowIndex].Items[itemIndex].Value['request_location']; 213 | if s = 'True' then 214 | begin 215 | //deprecated 216 | //Facebook.QuickReply.AddLocation; 217 | //sendAsButton := False; 218 | callbackData := 'text=_send_location'; 219 | end; 220 | s := CustomReplyData.Data.Items[rowIndex].Items[itemIndex].Value['request_contact']; 221 | if s = 'True' then 222 | begin 223 | Facebook.QuickReply.AddPhone; 224 | sendAsButton := False; 225 | end; 226 | 227 | if sendAsButton then 228 | Facebook.QuickReply.AddText(title,callbackData,image); 229 | end; 230 | 231 | end; 232 | Result := True; 233 | end; 234 | 235 | // GET Method Handler 236 | procedure TFacebookHandler.Get; 237 | begin 238 | //facebook chalenge 239 | // _GET['hub.mode'] <== subscribe 240 | // _GET['hub.verify_token'] 241 | Response.Content := _GET['hub.challenge']; 242 | if isEmpty(Response.Content) then 243 | OutputJson(400, ERR_INVALID_PARAMETER); 244 | end; 245 | 246 | // POST Method Handler 247 | procedure TFacebookHandler.Post; 248 | var 249 | j: integer; 250 | s, simg, mp3File, fbVoice: string; 251 | url, callName, callDesc, payloadText: String; 252 | lst: TStrings; 253 | isHandled, localReplyDisable, canSendMessage, canSendButton: boolean; 254 | replyText: TStringList; 255 | begin 256 | if _GET['_debug'] <> '1' then 257 | if not _DEVELOPMENT_ then CloseConnection('{}'); //ulil 258 | s := ''; 259 | canSendMessage := True; 260 | canSendButton := False; 261 | MessengerMode := mmFacebook; 262 | ChannelId := 'facebook'; 263 | Facebook.RequestContent := Request.Content; 264 | SessionController.SessionPrefix := 'facebook'; 265 | SessionController.SessionSuffix := Facebook.UserID; 266 | SessionController.ForceUniqueID := Facebook.UserID; 267 | SessionController.StartSession; 268 | 269 | LogUtil.Add(Request.Content, 'FB'); 270 | 271 | Text := Facebook.Text; 272 | Carik.UserPrefix := 'fb'; 273 | Carik.UserID := Facebook.UserID; 274 | SimpleBOT.SessionUserID := UniqueID; 275 | SimpleBOT.FirstSessionResponse := s2b(Config[FACEBOOK_BOT_FIRST_SESSION_RESPONSE]); 276 | 277 | Facebook.GetProfile(Facebook.UserID); 278 | 279 | localReplyDisable := s2b(Config[FACEBOOK_BOT_REPLY_DISABLE]); 280 | if (localReplyDisable or replyDisable) then 281 | begin 282 | LogChat(FACEBOOK_CHANNEL_ID, Carik.GroupChatID, Carik.GroupName, 283 | Facebook.UserID, Facebook.FullName, Facebook.FullName, Facebook.Text, '', 284 | Carik.IsGroup, True, 0, 0); //todo: Facebook.MessageID.AsInteger 285 | die('{"state":"silent"}'); 286 | exit; 287 | end; 288 | 289 | // voice processing 290 | if Facebook.IsVoice then 291 | begin 292 | fbVoice := 'ztemp/voice/' + Facebook.MessageID + '.mp4'; 293 | if FileExists(fbVoice) then 294 | DeleteFile(fbVoice); 295 | if not Facebook.DownloadVoiceTo(fbVoice) then 296 | begin 297 | Response.Content := '{"status":"voicefailed"}'; 298 | Exit; 299 | end; 300 | 301 | mp3File := 'ztemp/voice/' + Facebook.MessageID + '.mp3'; 302 | if FileExists(mp3File) then 303 | DeleteFile(mp3File); 304 | if Exec('./ffmpeg', ['-i', fbVoice, '-ac', '1', mp3File], s, swoNone) then 305 | begin 306 | with TWitAiIntegration.Create do 307 | begin 308 | Token := Config[WITAI_TOKEN]; 309 | //ContentType := Facebook.VoiceType; use default 310 | Text := trim(SpeechToText(mp3File)); 311 | if Text = '' then 312 | begin 313 | LogUtil.Add(ResultText, 'FB-voice'); 314 | end; 315 | Free; 316 | end; 317 | Prefix := SimpleBOT.GetResponse('VoiceResult'); 318 | Prefix := format(Prefix, [Text]) + '\n\n'; 319 | end; 320 | 321 | end;// end - voice processing 322 | 323 | if Facebook.isImage then 324 | begin 325 | Text := Facebook.ImageCaption; 326 | if Text = '' then 327 | Text := CMD_FULL_IMAGE_ANALYZE; 328 | if Pos('translate', Text) > 0 then 329 | begin 330 | Text := CMD_IMAGE_TRANSLATION; 331 | end; 332 | 333 | ImageID := Facebook.ImageID; //TODO: wrong ID,cek function get imageID 334 | ImageURL := Facebook.ImageURL; 335 | 336 | simg := 'FB-' + Carik.UserID + '-imgId-' + MessageID; 337 | s := SimpleBOT.UserData[simg]; 338 | if s = ImageURL then 339 | begin 340 | Exit; 341 | end 342 | else 343 | begin 344 | SimpleBOT.UserData[simg] := ImageURL; 345 | end; 346 | 347 | end; //-- isImage 348 | 349 | // Is Location 350 | if Facebook.IsLocation then 351 | begin 352 | SimpleBOT.UserData['LOC_LAT'] := FloatToStr(Facebook.LocationLatitude); 353 | SimpleBOT.UserData['LOC_LON'] := FloatToStr(Facebook.LocationLongitude); 354 | SimpleBOT.UserData['LOC_NAME'] := Facebook.LocationName; 355 | SimpleBOT.UserData['LOC_DATE'] := DateTimeToStr(Now); 356 | 357 | // still on topic, find location 358 | if ContextFocus <> '' then 359 | begin 360 | Text := ContextFocus + ' ' + SimpleBOT.UserData['LOC_LAT'] + 361 | ' ' + SimpleBOT.UserData['LOC_LON'] + ' ' + SimpleBOT.UserData['CONTEXT_DETAIL']; 362 | LogUtil.Add(Text, 'LOKASI'); 363 | end; 364 | 365 | // special for distance_fromto 366 | if ContextFocus = 'distance_fromto' then 367 | begin 368 | Text := 'Jarak dari ' + SimpleBOT.UserData['LOCATION_BASE'] + ' ke ' 369 | + SimpleBOT.UserData['LOC_NAME']; 370 | end; 371 | 372 | end; //-- Is Location 373 | 374 | if (Facebook.isPostback and (not Facebook.isReferral)) then 375 | begin 376 | Facebook.PayloadHandler['test'] := @payloadTestHandler; 377 | Facebook.PayloadHandler['TEXT'] := @payloadTextHandler; 378 | payloadText := Facebook.PayloadHandling; 379 | if payloadText.IsEmpty then 380 | begin 381 | lst := Explode(Facebook.Payload, '&'); 382 | payloadText := lst.Values['text']; 383 | lst.Free; 384 | end; 385 | 386 | // bypass 387 | payloadText := Facebook.PayloadTitle; 388 | 389 | if Text = '' then 390 | begin 391 | Text := SimpleBOT.GetResponse(payloadText); 392 | if isPayloadCommand(Text) then 393 | begin 394 | lst := Explode(Text, '|'); 395 | case lst[0] of 396 | 'call': 397 | begin 398 | if lst.Count > 2 then 399 | callName := lst[2]; 400 | if lst.Count > 3 then 401 | callDesc := lst[3]; 402 | Facebook.SendCall(Facebook.UserID, lst[1], callName, callDesc); 403 | end; 404 | 'url': 405 | begin 406 | if lst.Count > 3 then 407 | callDesc := lst[3]; 408 | url := lst[2]; 409 | url := url.Replace('%id%', Facebook.UserID); 410 | Facebook.SendButtonURL(Facebook.UserID, lst[1], url, callDesc); 411 | end; 412 | end; 413 | exit; 414 | end 415 | else 416 | begin 417 | if not Text.IsEmpty then 418 | begin 419 | // direct send from payload_response 420 | Text := Text.Replace('\n',#13); 421 | SimpleBOT.SimpleAI.ResponseText.Text := TrimFacebookMessage(Text); 422 | Facebook.Send(Facebook.UserID, SimpleBOT.SimpleAI.ResponseText.Text); 423 | Exit; 424 | end; 425 | Text := payloadText;//else 426 | end; 427 | end; // if text = '' 428 | 429 | if AppData.debug then 430 | begin 431 | LogUtil.Add( Facebook.ResultText, 'Payload'); 432 | end; 433 | end;// isPostback 434 | if (Facebook.isPostback and Facebook.isReferral) then //first time 435 | begin 436 | //Text := Facebook.ReferralRef; 437 | end; 438 | if Facebook.isReferral then //existing thread 439 | begin 440 | Text := Facebook.ReferralRef; 441 | end; 442 | 443 | if Facebook.isQuickReply then 444 | begin 445 | lst := Explode(Facebook.QuickReplyPayload, '&'); 446 | Text := lst.Values['text'].Trim; 447 | lst.Free; 448 | end; 449 | 450 | if Text = '' then 451 | begin 452 | Response.Content := '{"status":"empty"}'; 453 | Exit; 454 | end; 455 | OriginalText := Text; 456 | 457 | SimpleBOT.FirstSessionResponse := False; 458 | SimpleBOT.SecondSessionResponse := False; 459 | Carik.UserID := Facebook.UserID; 460 | Carik.UserPrefix := 'fb'; 461 | 462 | SimpleBOT.UserData['Name'] := Facebook.FirtName; 463 | SimpleBOT.UserData['FullName'] := Facebook.FullName; 464 | SimpleBOT.AdditionalParameters.Values['UserID'] := 'fb-' + Facebook.UserID; 465 | if not isEmpty( Facebook.MessageID.Trim) then 466 | SimpleBOT.AdditionalParameters.Values['ChatID'] := 'fb-' + Facebook.MessageID; 467 | 468 | SimpleBOT.AdditionalParameters.Values['FullName'] := Facebook.FullName; 469 | SimpleBOT.AdditionalParameters.Values['full_name'] := Facebook.FullName; 470 | 471 | // check if any custom handler 472 | isHandled := False; 473 | if Assigned(FOnMessage) then 474 | begin 475 | replyText := TStringList.Create; 476 | replyText.Text := FOnMessage(OriginalText, isHandled); 477 | for j:=0 to SimpleBOT.AdditionalParameters.Count-1 do 478 | begin 479 | s := SimpleBOT.AdditionalParameters.Names[j]; 480 | SimpleBOT.SimpleAI.Parameters.Values[s] := SimpleBOT.AdditionalParameters.ValueFromIndex[j]; //manual add parameter 481 | end; 482 | end; 483 | 484 | if FormInputHandler() then 485 | begin 486 | isHandled := True; 487 | end; 488 | 489 | if not isHandled then 490 | Text := GenerateTextFromCustomActionOption(Text); 491 | 492 | Text := Text.Replace(',',''); 493 | if not isHandled then 494 | begin 495 | BotInit; 496 | Response.Content := ProcessText(Text);//ulil 497 | SimpleBOT.SimpleAI.ResponseText.Text := RemoveMarkDown(RemoveDummyImageLink(SimpleBOT.SimpleAI.ResponseText.Text)).Trim; 498 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 499 | end else begin 500 | SimpleBOT.SimpleAI.ResponseText.Text := replyText.Text; 501 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 502 | replyText.Free; 503 | end; 504 | 505 | s := Facebook.Text; 506 | if Facebook.isPostback then 507 | begin 508 | s := 'callback|'+SimpleBOT.SimpleAI.IntentName; 509 | end; 510 | LogChat(FACEBOOK_CHANNEL_ID, Carik.GroupChatID, Carik.GroupName, 511 | Carik.UserID, Facebook.FullName, Facebook.FullName, s, SimpleBOT.SimpleAI.ResponseText.Text, 512 | Carik.IsGroup, True); 513 | //if not TELEGRAM.IsGroup then 514 | begin 515 | if IsUserSuspended(FACEBOOK_CHANNEL_ID, Carik.UserID) then 516 | begin 517 | if AppData.debug then 518 | LogUtil.Add(Carik.UserID + ' suspended', 'USERCHECK'); 519 | Exit; 520 | end; 521 | end; 522 | 523 | if IsCommand(SimpleBOT.SimpleAI.ResponseText.Text) then 524 | begin 525 | //xxx 526 | end; 527 | 528 | //Exec Command - carik base 529 | if Carik.IsCommand(SimpleBOT.SimpleAI.ResponseText.Text) then 530 | begin 531 | SimpleBOT.SimpleAI.ResponseText.Text := 532 | Carik.ExecCommand(SimpleBOT.SimpleAI.ResponseText.Text); 533 | 534 | if SimpleBOT.SimpleAI.ResponseText.Text = '' then 535 | SimpleBOT.SimpleAI.ResponseText.Text := 536 | SimpleBOT.GetResponse('DataTidakAdaResponse'); 537 | //TODO: generate user data and object 538 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 539 | end; 540 | 541 | if _DEVELOPMENT_ then Exit;//ulil 542 | 543 | if IsCustomAction then 544 | begin 545 | //SaveActionToUserData; 546 | if CustomReplyType = 'button' then 547 | begin 548 | canSendButton := True; 549 | canSendMessage := False; 550 | ButtonCaption := SimpleBOT.SimpleAI.ResponseText.Text; 551 | if ButtonCaption.Length > 640 then 552 | begin 553 | canSendMessage := True; 554 | ButtonCaption := '📋 Pilihan lain'; 555 | end; 556 | end; 557 | if CustomReplyType = 'card' then 558 | begin 559 | ElementArray := TJSONArray(CustomReplyData.Data); 560 | CanSendTemplateCard := true; 561 | SimpleBOT.SimpleAI.ResponseText.Text := ''; 562 | ButtonCaption := SimpleBOT.SimpleAI.CustomReply['action/button_title']; 563 | if ButtonCaption.IsEmpty then 564 | ButtonCaption := 'Detail'; 565 | end; 566 | if CustomReplyType = 'quickreply' then 567 | begin 568 | { 569 | manual test 570 | Facebook.QuickReply.AddText('gempa', 'info gempa', 'https://i.pinimg.com/originals/39/44/6c/39446caa52f53369b92bc97253d2b2f1.png'); 571 | Facebook.QuickReply.AddText('satu', 'echo satu', 'https://i.pinimg.com/originals/39/44/6c/39446caa52f53369b92bc97253d2b2f1.png'); 572 | Facebook.QuickReply.AddText('dua', 'echo dua', 'https://i.pinimg.com/originals/39/44/6c/39446caa52f53369b92bc97253d2b2f1.png'); 573 | Facebook.SendQuickReply(Facebook.UserID, 'contoh'); 574 | } 575 | generateQuickReplay; 576 | canSendMessage := False; 577 | end; 578 | if ((CustomReplyType = 'menu') or (CustomReplyType = 'list')) then 579 | begin 580 | SaveActionToUserData(CustomReplyType, CustomReplyData.Data); 581 | if not CustomActionAsText.IsEmpty then 582 | begin 583 | SimpleBOT.SimpleAI.ResponseText.Text := SimpleBOT.SimpleAI.ResponseText.Text.Trim 584 | + '\n' + ACTION_CAPTION + '\n' + CustomActionAsText.Replace(#10,'\n'); 585 | if CustomActionSuffix.IsNotEmpty then 586 | SimpleBOT.SimpleAI.ResponseText.Text := SimpleBOT.SimpleAI.ResponseText.Text.Trim 587 | + '\n' + CustomActionSuffix.Replace(#10,'\n'); 588 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 589 | end; 590 | end; 591 | if CustomReplyType = 'form' then 592 | begin 593 | canSendMessage := True; 594 | end; 595 | end; 596 | 597 | if not Prefix.IsEmpty then 598 | begin 599 | SimpleBOT.SimpleAI.ResponseText[0] := Prefix + SimpleBOT.SimpleAI.ResponseText[0]; 600 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 601 | end; 602 | if not Suffix.IsEmpty then 603 | begin 604 | if SimpleBOT.SimpleAI.ResponseText.Count = 0 then 605 | SimpleBOT.SimpleAI.ResponseText.Add(Suffix) 606 | else 607 | begin 608 | j := SimpleBOT.SimpleAI.ResponseText.Count-1; 609 | SimpleBOT.SimpleAI.ResponseText[j] := SimpleBOT.SimpleAI.ResponseText[j] + Suffix; 610 | end; 611 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 612 | end; 613 | 614 | if SendRichContent then 615 | begin 616 | die('...rich...'); 617 | exit; 618 | //LINE.Push(line.UserID, RichContent, True); 619 | //LogUtil.Add( LINE.ResultText, 'FB-Rich'); 620 | end; 621 | 622 | // send 623 | SimpleBOT.SimpleAI.ResponseText.Text := 624 | StringReplace(SimpleBOT.SimpleAI.ResponseText.Text, 625 | '\n', #10, [rfReplaceAll]); 626 | SimpleBOT.SimpleAI.ResponseText.Text := 627 | TrimFacebookMessage(SimpleBOT.SimpleAI.ResponseText.Text); 628 | 629 | if canSendMessage then 630 | begin 631 | Facebook.Send(Facebook.UserID, SimpleBOT.SimpleAI.ResponseText.Text); 632 | if not Facebook.IsSuccessfull then 633 | begin 634 | LogUtil.Add(Facebook.ResultText, 'FB'); 635 | end; 636 | end; 637 | 638 | // if speaking mode 639 | if SpeakingMode then 640 | begin 641 | if Config[CARIK_TTS_URL] <> '' then 642 | begin 643 | s := PrepareTextToSpeech(SimpleBOT.SimpleAI.ResponseText.Text); 644 | if s <> '' then 645 | begin 646 | s := Config[CARIK_TTS_URL] + s; 647 | Facebook.SendAudio(Facebook.UserID, s); 648 | end; 649 | end; 650 | end; 651 | 652 | if SendAudio then 653 | begin 654 | Facebook.SendAudio(Facebook.UserID, FileURL); 655 | end; 656 | 657 | if SendPhoto then 658 | begin 659 | Facebook.SendImage(Facebook.UserID, FileURL); 660 | Facebook.Send(Facebook.UserID,ImageCaption); 661 | end; 662 | 663 | if SendQuickReplayLocation then 664 | Facebook.QuickReply.AddLocation; 665 | if Facebook.QuickReply.Count > 0 then 666 | begin 667 | Facebook.SendQuickReply(Facebook.UserID, SimpleBOT.SimpleAI.ResponseText.Text); 668 | end; 669 | 670 | if canSendButton then 671 | begin 672 | if sendButton(ButtonCaption, CustomReplyData) then 673 | begin 674 | canSendMessage := False; 675 | end; 676 | end; 677 | 678 | if CanSendTemplateCard then 679 | Facebook.SendTemplateCard(Facebook.UserID, ElementArray, ButtonCaption); 680 | 681 | s := jsonGetData(SimpleBOT.SimpleAI.CustomReply.Data, 'suffix'); 682 | if s.IsNotEmpty then 683 | Facebook.Send(Facebook.UserID, s); 684 | 685 | 686 | s := Text; 687 | if Facebook.isPostback then 688 | begin 689 | s := 'callback|'+SimpleBOT.SimpleAI.IntentName; 690 | end; 691 | Analytics('facebook', SimpleBOT.SimpleAI.IntentName, s, 'fb-' + Carik.UserID); 692 | end; 693 | 694 | 695 | 696 | end. 697 | -------------------------------------------------------------------------------- /source/common/line_handler.pas: -------------------------------------------------------------------------------- 1 | unit line_handler; 2 | 3 | {$mode objfpc}{$H+} 4 | 5 | interface 6 | 7 | uses 8 | {$if FPC_FULlVERSION >= 30200} 9 | opensslsockets, fpopenssl, 10 | {$endif} 11 | carik_webmodule, logutil_lib, json_lib, 12 | line_integration, simplebot_controller, carik_controller, 13 | fpjson, 14 | Classes, SysUtils, fpcgi, HTTPDefs, fastplaz_handler, database_lib, string_helpers, json_helpers; 15 | 16 | {$include ../common/carik.inc} 17 | _DEVELOPMENT_ = False; 18 | 19 | type 20 | 21 | { TLineHandler } 22 | 23 | TLineHandler = class(TCarikWebModule) 24 | private 25 | FOnMessage: TOnMessageEvent; 26 | FOnSpam: TOnSpamEvent; 27 | forceRespond: boolean; 28 | LINE: TLineIntegration; 29 | procedure BeforeRequestHandler(Sender: TObject; ARequest: TRequest); 30 | 31 | function sendButton(ACaption: string; ADataAsJson: TJSONUtil; AImageDefault: string; AsQuickReply: boolean = False): boolean; 32 | function sendCard(ADataAsJson: TJSONUtil; AImageDefault: string): boolean; 33 | function sendCard(ADataAsArray: TJSONArray; AImageDefault: string): boolean; 34 | public 35 | ReplyToken: string; 36 | constructor CreateNew(AOwner: TComponent; CreateMode: integer); override; 37 | destructor Destroy; override; 38 | Property OnMessage : TOnMessageEvent Read FOnMessage Write FOnMessage; 39 | Property OnSpam : TOnSpamEvent Read FOnSpam Write FOnSpam; 40 | 41 | procedure Get; override; 42 | procedure Post; override; 43 | end; 44 | 45 | implementation 46 | 47 | uses common; 48 | 49 | constructor TLineHandler.CreateNew(AOwner: TComponent; CreateMode: integer); 50 | var 51 | s: string; 52 | begin 53 | inherited CreateNew(AOwner, CreateMode); 54 | BeforeRequest := @BeforeRequestHandler; 55 | 56 | // is custom Bot ? 57 | s := Trim(_GET['botid']); 58 | if s <> '' then 59 | begin 60 | //Config.Filename := 'config/config-' + s + '.json'; 61 | //SimpleBOT.StorageFileName := 'files/' + s + '-data/carik-userdata.dat'; 62 | //SimpleBOT.LoadConfig(''); //todo: gagal load 63 | end; 64 | 65 | LINE := TLineIntegration.Create; 66 | LINE.BotName := BOTNAME_DEFAULT; 67 | LINE.Token := Config['line/default/token']; 68 | forceRespond := False; 69 | end; 70 | 71 | destructor TLineHandler.Destroy; 72 | begin 73 | inherited Destroy; 74 | end; 75 | 76 | // Init First 77 | procedure TLineHandler.BeforeRequestHandler(Sender: TObject; ARequest: TRequest); 78 | begin 79 | Response.ContentType := 'application/json'; //TODO: uncomment 80 | end; 81 | 82 | function TLineHandler.sendButton(ACaption: string; ADataAsJson: TJSONUtil; 83 | AImageDefault: string; AsQuickReply: boolean): boolean; 84 | var 85 | i, j, itemCount, captionLength: integer; 86 | s, itemLabel, itemType, itemData, itemURI, itemImage, templateAsString: string; 87 | buttonList, itemAsArray: TJSONArray; 88 | 89 | procedure _generateButtonList(AData: TJSONArray; var Output: TJSONArray); 90 | var 91 | rowIndex, itemIndex: integer; 92 | s, url, callbackData, image: string; 93 | sourceRowData: TJSONUtil; 94 | buttonData: TJSONObject; 95 | lst: TStrings; 96 | begin 97 | if AData.Count = 0 then 98 | Exit; 99 | itemCount := 0; 100 | sourceRowData := TJSONUtil.Create; 101 | for rowIndex := 0 to AData.Count - 1 do 102 | begin 103 | sourceRowData.LoadFromJsonString(AData.Items[rowIndex].AsJSON, False); 104 | for itemIndex := 0 to TJSONArray(sourceRowData.Data).Count - 1 do 105 | begin 106 | itemCount := itemCount + 1; 107 | if not AsQuickReply then 108 | if itemCount > 4 then 109 | Break; 110 | s := TJSONArray(sourceRowData.Data).Items[itemIndex].ValueOfNameAsString('text'); 111 | callbackData := TJSONArray(sourceRowData.Data).Items[itemIndex].ValueOfNameAsString('callback_data'); 112 | url := TJSONArray(sourceRowData.Data).Items[itemIndex].ValueOfNameAsString('url'); 113 | image := TJSONArray(sourceRowData.Data).Items[itemIndex].ValueOfNameAsString('image'); 114 | 115 | buttonData := TJSONObject.Create; 116 | buttonData.Add('label', s); 117 | 118 | // url 119 | if not url.IsEmpty then 120 | begin 121 | buttonData.Add('type', 'uri'); 122 | buttonData.Add('uri', url); 123 | end; 124 | 125 | // callback data 126 | if not callbackData.IsEmpty then 127 | begin 128 | lst := Explode(callbackData, '&'); 129 | if not lst.Values['text'].IsEmpty then 130 | begin 131 | buttonData.Add('type', 'postback'); 132 | buttonData.Add('data', 'text='+lst.Values['text'].Trim); 133 | buttonData.Add('textReply', lst.Values['text'].Trim); 134 | end; 135 | lst.Free; 136 | end; 137 | 138 | if not image.IsEmpty then 139 | begin 140 | buttonData.Add('image', image); 141 | end; 142 | Output.Add(buttonData); 143 | end; 144 | 145 | end; 146 | sourceRowData.Free; 147 | end; 148 | 149 | begin 150 | Response.Content:= ''; 151 | Result := False; 152 | if ADataAsJson.Data.Count = 0 then 153 | Exit; 154 | 155 | ACaption := ACaption.Replace('\n', #10); 156 | 157 | buttonList := TJSONArray.Create; 158 | _generateButtonList(TJSONArray(ADataAsJson.Data), buttonList); 159 | 160 | 161 | if itemCount > 4 then 162 | begin 163 | // send as text message 164 | //ulil: ..... 165 | end 166 | else 167 | begin 168 | 169 | end;//if itemCount > 4 then 170 | 171 | // generate quick reply 172 | if AsQuickReply then 173 | begin 174 | itemAsArray := TJSONArray.Create; 175 | for i := 0 to buttonList.Count-1 do 176 | begin 177 | itemType := buttonList.Items[i].Value['type']; 178 | itemLabel := buttonList.Items[i].Value['label']; 179 | itemData := buttonList.Items[i].Value['textReply']; 180 | itemImage := buttonList.Items[i].Value['image']; 181 | 182 | with TJSONUtil.Create do 183 | begin 184 | Value['type'] := 'action'; 185 | if not itemImage.IsEmpty then 186 | Value['imageUrl'] := itemImage; 187 | Value['action/type'] := 'message'; 188 | Value['action/label'] := itemLabel; 189 | Value['action/text'] := itemData; 190 | 191 | itemAsArray.Add(Data); 192 | end; 193 | 194 | end; 195 | 196 | with TJSONUtil.Create do 197 | begin 198 | Value['type'] := 'text'; 199 | Value['text'] := ACaption; 200 | ValueArray['quickReply/items'] := itemAsArray; 201 | 202 | LINE.Push( LINE.UserID, AsJSON, true); 203 | 204 | Free; 205 | end; 206 | 207 | buttonList.Free; 208 | Exit; 209 | end; 210 | 211 | // generate line button template 212 | with TLineTemplateMessage.Create('buttons') do 213 | begin 214 | AltText := 'Pilihan'; 215 | Title := ' '; 216 | Text := ACaption; 217 | s := UTF8ToString(ACaption); 218 | captionLength := s.Length; 219 | if captionLength > 60 then 220 | Text := 'Pilihan:'; 221 | ThumbnailImageURL := AImageDefault; 222 | 223 | for i := 0 to buttonList.Count-1 do 224 | begin 225 | itemType := buttonList.Items[i].Value['type']; 226 | itemLabel := buttonList.Items[i].Value['label']; 227 | if itemType = 'message' then 228 | begin 229 | itemData := buttonList.Items[i].Value['data']; 230 | AddActionMessage(itemLabel, itemData) 231 | end; 232 | if itemType = 'postback' then 233 | begin 234 | itemData := buttonList.Items[i].Value['data']; 235 | AddActionPostBack(itemLabel, itemData) 236 | end; 237 | if itemType = 'uri' then 238 | begin 239 | itemURI := buttonList.Items[i].Value['uri']; 240 | AddActionURI(itemLabel, itemURI); 241 | end; 242 | end; 243 | templateAsString := AsJSON; 244 | 245 | //Send to User 246 | s := ACaption; 247 | s := preg_replace('\*(.*?)\*', '$1', s); 248 | s := preg_replace('\[(.*?)\]\((.*?)\)', '$1, $2', s); // url 249 | ACaption := s; 250 | if captionLength > 60 then 251 | LINE.Send( LINE.UserID, ACaption); 252 | LINE.Push( LINE.UserID, templateAsString, true); 253 | Free; 254 | end; 255 | 256 | buttonList.Free; 257 | Result := True; 258 | end; 259 | 260 | function TLineHandler.sendCard(ADataAsJson: TJSONUtil; AImageDefault: string 261 | ): boolean; 262 | var 263 | i: integer; 264 | cardTitle, subTitle, actionType, actionData: string; 265 | cardList: TLineTemplateMessage; 266 | cardItem: TJSONUtil; 267 | actionAsArray: TJSONArray; 268 | begin 269 | Result := False; 270 | ElementArray := TJSONArray(ADataAsJson.Data); 271 | 272 | cardList := TLineTemplateMessage.Create('carousel'); 273 | cardList.AltText := 'Tanggapan Anda'; 274 | cardList.Title := 'Perlu tanggapan Anda'; 275 | cardList.Text := 'Silahkan Pilih:'; 276 | 277 | Response.Content:=''; 278 | for i := 0 to ElementArray.Count-1 do 279 | begin 280 | //if i = 5 then 281 | // Break; 282 | cardTitle := ElementArray.Items[i].Value['title']; 283 | if cardTitle.Length > 40 then 284 | cardTitle := cardTitle.Substring(0,37)+'...'; 285 | subTitle := ElementArray.Items[i].Value['sub_title']; 286 | if subTitle.Length > 60 then 287 | subTitle := subTitle.Substring(0,56)+'...'; 288 | cardItem := TJSONUtil.Create; 289 | cardItem['type'] := 'buttons'; 290 | cardItem['title'] := cardTitle; 291 | cardItem['text'] := subTitle; 292 | cardItem['thumbnailImageUrl'] := ElementArray.Items[i].Value['image_url']; 293 | 294 | actionAsArray := TJSONArray.Create; 295 | ButtonCaption := SimpleBOT.SimpleAI.CustomReply['action/button_title']; 296 | if ButtonCaption.IsEmpty then 297 | ButtonCaption := 'Info lanjut'; 298 | 299 | actionType := 'uri'; 300 | actionData := ElementArray.Items[i].Value['url']; 301 | if actionData.IsEmpty then 302 | begin 303 | actionType := 'postback'; 304 | actionData := ElementArray.Items[i].Value['callback_data']; 305 | end; 306 | with TJSONUtil.Create do 307 | begin 308 | Value['type'] := actionType; 309 | Value['label'] := 'Detail'; 310 | if actionType = 'uri' then 311 | Value['uri'] := actionData; 312 | if actionType = 'postback' then 313 | begin 314 | Value['data'] := actionData; 315 | //bValue['text'] := cardTitle; 316 | end; 317 | actionAsArray.Add(Data); 318 | end; 319 | cardItem.Data.Add('actions', actionAsArray); 320 | 321 | cardList.AddColumnAsJson(cardItem.AsJSON); 322 | cardItem.Free; 323 | end; 324 | LINE.Push( line.UserID, cardList.AsJSON, true); 325 | 326 | cardList.Free; 327 | Result := True; 328 | end; 329 | 330 | function TLineHandler.sendCard(ADataAsArray: TJSONArray; AImageDefault: string 331 | ): boolean; 332 | var 333 | i: integer; 334 | cardTitle, subTitle, imgUrl : string; 335 | cardList: TLineTemplateMessage; 336 | cardItem: TJSONUtil; 337 | actionAsArray: TJSONArray; 338 | begin 339 | Result := False; 340 | cardList := TLineTemplateMessage.Create('carousel'); 341 | cardList.AltText := 'Tanggapan Anda'; 342 | cardList.Title := 'Perlu tanggapan Anda'; 343 | cardList.Text := 'Silahkan Pilih:'; 344 | 345 | Response.Content:=''; 346 | for i := 0 to ADataAsArray.Count-1 do 347 | begin 348 | //if i = 5 then 349 | // Break; 350 | cardTitle := ADataAsArray.Items[i].Value['title']; 351 | if cardTitle.Length > 40 then 352 | cardTitle := cardTitle.Substring(0,37)+'...'; 353 | subTitle := ADataAsArray.Items[i].Value['sub_title']; 354 | if subTitle.Length > 60 then 355 | subTitle := subTitle.Substring(0,56)+'...'; 356 | cardItem := TJSONUtil.Create; 357 | cardItem['type'] := 'buttons'; 358 | cardItem['title'] := cardTitle; 359 | cardItem['text'] := subTitle; 360 | imgUrl := ADataAsArray.Items[i].Value['image_url']; 361 | imgUrl := 'https://services.carik.id/img/u/' + UrlEncode(UrlEncode(imgUrl)); //ulil: masukkan dalam config 362 | cardItem['thumbnailImageUrl'] := imgUrl; 363 | 364 | actionAsArray := TJSONArray.Create; 365 | ButtonCaption := SimpleBOT.SimpleAI.CustomReply['action/button_title']; 366 | if ButtonCaption.IsEmpty then 367 | ButtonCaption := 'Info lanjut'; 368 | with TJSONUtil.Create do 369 | begin 370 | Value['type'] := 'uri'; 371 | Value['label'] := 'Detail'; 372 | Value['uri'] := ADataAsArray.Items[i].Value['url']; 373 | actionAsArray.Add(Data); 374 | end; 375 | cardItem.Data.Add('actions', actionAsArray); 376 | 377 | cardList.AddColumnAsJson(cardItem.AsJSON); 378 | cardItem.Free; 379 | end; 380 | LINE.Push( line.UserID, cardList.AsJSON, true); 381 | 382 | cardList.Free; 383 | Result := True; 384 | 385 | end; 386 | 387 | // GET Method Handler 388 | procedure TLineHandler.Get; 389 | begin 390 | Response.Content := '{}'; 391 | end; 392 | 393 | // POST Method Handler 394 | // CURL example: 395 | // curl -X POST -H "Authorization: Basic dW5hbWU6cGFzc3dvcmQ=" "yourtargeturl" 396 | procedure TLineHandler.Post; 397 | var 398 | j: integer; 399 | template, s, lineVoice: string; 400 | isHandled, canSendMessage, canSendButton, canSendQuickReply, canSendCard: boolean; 401 | replyText: TStringList; 402 | begin 403 | if not _DEVELOPMENT_ then CloseConnection('{}'); //ulil 404 | MessengerMode := mmLine; 405 | canSendMessage := True; 406 | canSendButton := False; 407 | canSendQuickReply := False; 408 | canSendCard := False; 409 | ChannelId := 'line'; 410 | LINE.RequestContent := Request.Content; 411 | LogUtil.Add(Request.Content, 'LINE'); 412 | 413 | SessionController.SessionPrefix := 'line'; 414 | SessionController.SessionSuffix := LINE.UserID; 415 | SessionController.ForceUniqueID := LINE.UserID; 416 | SessionController.StartSession; 417 | 418 | LogUtil.Add(Request.Content, 'LINE'); 419 | 420 | LINE.GetProfile(LINE.UserID); 421 | ReplyToken := LINE.ReplyToken; 422 | Carik.UserPrefix := 'ln'; 423 | Carik.UserID := LINE.UserID; 424 | Carik.UserName := LINE.UserProfile['displayName'];//&pictureUrl 425 | SimpleBOT.SessionUserID := UniqueID; 426 | SimpleBOT.FirstSessionResponse := s2b(Config[LINE_BOT_FIRST_SESSION_RESPONSE]); 427 | 428 | if LINE.isVoice then 429 | begin 430 | lineVoice := 'ztemp/cache/' + LINE.MessageID + '.mp4'; 431 | if FileExists(lineVoice) then 432 | DeleteFile(lineVoice); 433 | if not LINE.GetContent(LINE.MessageID, lineVoice) then 434 | begin 435 | Response.Content := '{"status":"voicefailed"}'; 436 | Exit; 437 | end; 438 | 439 | Text := SpeechToText(lineVoice); 440 | 441 | if Text <> '' then 442 | begin 443 | s := SimpleBOT.GetResponse('VoiceResult'); 444 | s := format(s, [Text]); 445 | s := TrimLineMessage(s); 446 | LINE.Reply(ReplyToken, s); 447 | forceRespond := True; 448 | end 449 | else 450 | begin 451 | s := SimpleBOT.GetResponse('VoiceResultNone'); 452 | s := StringReplace(s, '%username%', '', [rfReplaceAll]); 453 | s := TrimLineMessage(s); 454 | LINE.Reply(ReplyToken, s); 455 | Exit; 456 | end; 457 | 458 | end;//-- isVoice 459 | 460 | 461 | if LINE.isPostback then 462 | begin 463 | Text := LINE.PostbackData.Values['text']; 464 | if not Text.IsEmpty then 465 | forceRespond := True; 466 | end; 467 | 468 | if not forceRespond then 469 | begin 470 | if LINE.isMessage then 471 | begin 472 | Text := LINE.Text; 473 | end 474 | else 475 | begin 476 | if not LINE.isJoinToGroup then 477 | Exit; 478 | Text := '/invitation carikbot'; 479 | end; 480 | end; 481 | 482 | // is Location ? 483 | if LINE.isLocation then 484 | begin 485 | SimpleBOT.UserData['LOC_LAT'] := FloatToStr(LINE.LocationLatitude); 486 | SimpleBOT.UserData['LOC_LON'] := FloatToStr(LINE.LocationLongitude); 487 | SimpleBOT.UserData['LOC_NAME'] := LINE.LocationName; 488 | SimpleBOT.UserData['LOC_DATE'] := DateTimeToStr(Now); 489 | 490 | if ObjectFocus <> '' then 491 | begin 492 | Text := ObjectFocus + ' ' + SimpleBOT.UserData['LOC_LAT'] + 493 | ' ' + SimpleBOT.UserData['LOC_LON'] + ' ' + SimpleBOT.UserData['OBJECT_DETAIL']; 494 | end; 495 | 496 | end;//--- is location - end 497 | 498 | // is image ? 499 | if LINE.isImage then 500 | begin 501 | s := 'ztemp/cache/' + LINE.MessageID + '.jpg'; 502 | if FileExists(s) then 503 | DeleteFile(s); 504 | if not LINE.GetContent(LINE.MessageID, s) then 505 | begin 506 | Response.Content := '{"status":"imagefailed"}'; 507 | Exit; 508 | end; 509 | Text := CMD_FULL_IMAGE_ANALYZE; 510 | ImageID := LINE.MessageID; 511 | ImageURL := 'https://fire.carik.id/carik/' + s; // TODO: ganti url 512 | LogUtil.Add(ImageURL, 'LINE'); 513 | end;//--- is image - end 514 | 515 | Carik.UserPrefix := 'lm'; 516 | Carik.UserID := LINE.UserID; 517 | if LINE.isGroup then 518 | begin 519 | if not LINE.isMentioned then 520 | Exit; 521 | SimpleBOT.FirstSessionResponse := True; 522 | SimpleBOT.SecondSessionResponse := True; 523 | Carik.GroupChatID := LINE.GroupID; 524 | Carik.GroupName := LINE.GroupName; 525 | end; 526 | 527 | if LINE.isSticker then 528 | begin 529 | s := SimpleBOT.GetResponse('LINEEmojiResponse'); 530 | ReplyToken := LINE.ReplyToken; 531 | LINE.SendSticker(ReplyToken, '1', s); 532 | Exit; 533 | end; 534 | 535 | if Text = '' then 536 | begin 537 | Response.Content := '{"status":"empty"}'; 538 | Exit; 539 | end; 540 | 541 | OriginalText := Text; 542 | 543 | // check if any custom handler 544 | isHandled := False; 545 | if Assigned(FOnMessage) then 546 | begin 547 | replyText := TStringList.Create; 548 | replyText.Text := FOnMessage(OriginalText, isHandled); 549 | for j:=0 to SimpleBOT.AdditionalParameters.Count-1 do 550 | begin 551 | s := SimpleBOT.AdditionalParameters.Names[j]; 552 | SimpleBOT.SimpleAI.Parameters.Values[s] := SimpleBOT.AdditionalParameters.ValueFromIndex[j]; //manual add parameter 553 | end; 554 | end; 555 | 556 | if FormInputHandler() then 557 | begin 558 | isHandled := True; 559 | Suffix := Suffix.Replace('\n', #10); 560 | end; 561 | 562 | if not isHandled then 563 | Text := GenerateTextFromCustomActionOption(Text); 564 | 565 | SimpleBOT.AdditionalParameters.Values['FullName'] := Carik.FullName; 566 | SimpleBOT.AdditionalParameters.Values['full_name'] := Carik.FullName; 567 | 568 | if not isHandled then 569 | begin 570 | BotInit; 571 | Response.Content := ProcessText(Text); 572 | SimpleBOT.SimpleAI.ResponseText.Text := RemoveDummyImageLink(SimpleBOT.SimpleAI.ResponseText.Text).Trim; 573 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 574 | end 575 | else 576 | begin 577 | SimpleBOT.SimpleAI.ResponseText.Text := replyText.Text; 578 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 579 | replyText.Free; 580 | end; 581 | //exit; //ulil 582 | 583 | SimpleBOT.SimpleAI.ResponseText.Text := 584 | StringReplace(SimpleBOT.SimpleAI.ResponseText.Text, '\n', #10, [rfReplaceAll]); 585 | 586 | // custom action: button, quickreply 587 | if IsCustomAction then 588 | begin 589 | SaveActionToUserData(CustomReplyType, CustomReplyData.Data); 590 | ButtonCaption := SimpleBOT.SimpleAI.ResponseText.Text; 591 | if CustomReplyType = 'button' then 592 | begin 593 | canSendButton := True; 594 | canSendMessage := False; 595 | end; 596 | if CustomReplyType = 'quickreply' then 597 | begin 598 | canSendQuickReply := True; 599 | canSendMessage := False; 600 | end; 601 | if ((CustomReplyType = 'menu') or (CustomReplyType = 'list')) then 602 | begin 603 | if not CustomActionAsText.IsEmpty then 604 | begin 605 | SimpleBOT.SimpleAI.ResponseText.Text := SimpleBOT.SimpleAI.ResponseText.Text.Trim 606 | + #10 + ACTION_CAPTION + #10 + CustomActionAsText; 607 | if CustomActionSuffix.IsNotEmpty then 608 | SimpleBOT.SimpleAI.ResponseText.Text := SimpleBOT.SimpleAI.ResponseText.Text.Trim 609 | + '\n' + CustomActionSuffix.Replace(#10,'\n'); 610 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 611 | end; 612 | end; 613 | if CustomReplyType = 'card' then 614 | begin 615 | canSendCard := True; 616 | canSendMessage := False; 617 | end; 618 | if CustomReplyType = 'form' then 619 | begin 620 | canSendMessage := True; 621 | end; 622 | 623 | end; 624 | 625 | if not Prefix.IsEmpty then 626 | begin 627 | SimpleBOT.SimpleAI.ResponseText[0] := Prefix + SimpleBOT.SimpleAI.ResponseText[0]; 628 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 629 | end; 630 | if not Suffix.IsEmpty then 631 | begin 632 | if SimpleBOT.SimpleAI.ResponseText.Count = 0 then 633 | SimpleBOT.SimpleAI.ResponseText.Add(Suffix) 634 | else 635 | begin 636 | j := SimpleBOT.SimpleAI.ResponseText.Count-1; 637 | SimpleBOT.SimpleAI.ResponseText[j] := SimpleBOT.SimpleAI.ResponseText[j] + Suffix; 638 | end; 639 | Response.Content := SimpleBOT.SimpleAI.ResponseJson; 640 | end; 641 | 642 | // reply message 643 | ReplyToken := LINE.ReplyToken; 644 | SimpleBOT.SimpleAI.ResponseText.Text := 645 | TrimLineMessage(RemoveMarkDown(SimpleBOT.SimpleAI.ResponseText.Text)); 646 | 647 | // remove markdown 648 | s := (SimpleBOT.SimpleAI.ResponseText.Text); 649 | s := preg_replace('\*(.*?)\*', '$1', s); 650 | s := preg_replace('\[(.*?)\]\((.*?)\)', '$1, $2', s); // url 651 | SimpleBOT.SimpleAI.ResponseText.Text := s; 652 | if canSendMessage then 653 | begin 654 | if forceRespond then 655 | LINE.Send(LINE.UserID, SimpleBOT.SimpleAI.ResponseText.Text) 656 | else 657 | LINE.Reply(ReplyToken, SimpleBOT.SimpleAI.ResponseText.Text); 658 | end; 659 | if SimpleBOT.Debug then 660 | LogUtil.Add( LINE.ResultText, 'LINE'); 661 | 662 | if SpeakingMode then 663 | begin 664 | if Config[CARIK_TTS_URL] <> '' then 665 | begin 666 | s := PrepareTextToSpeech(SimpleBOT.SimpleAI.ResponseText.Text); 667 | 668 | // TODO: 669 | //1. generate URL text2speech, jika lebih dari 200 karakter, pake post method. 670 | //2. lokasi monumen, gedung, keluar errornya, tapi ada. 671 | 672 | 673 | // todo: prepare post url text2speech 674 | if s <> '' then 675 | begin 676 | LINE.Debug := True; 677 | LINE.SendAudio(LINE.UserID, Config[CARIK_TTS_URL] + s); 678 | end; 679 | end; 680 | end; 681 | 682 | 683 | if canSendButton then 684 | begin 685 | if sendButton(ButtonCaption, CustomReplyData, '') then 686 | begin 687 | //canSendMessage := False; 688 | end; 689 | end; 690 | 691 | if canSendQuickReply then 692 | begin 693 | if sendButton(ButtonCaption, CustomReplyData, '', True) then 694 | begin 695 | end; 696 | end; 697 | 698 | if canSendCard then 699 | begin 700 | if sendCard(CustomReplyData, '') then 701 | begin 702 | 703 | end; 704 | end; 705 | if CanSendTemplateCard then //todo: duplicate with canSendCard 706 | begin 707 | sendCard(ElementArray, ''); 708 | end; 709 | 710 | if SendVenue then 711 | begin 712 | LINE.SendLocation(LINE.UserID, VenueName, VenueAddress, VenueLatitude, 713 | VenueLongitude); 714 | end; 715 | 716 | if SendAudio then 717 | begin 718 | LINE.Debug := True; 719 | LINE.SendAudio(LINE.UserID, FileURL); 720 | LogUtil.Add( LINE.ResultText, 'LINE'); 721 | end; 722 | 723 | if SendPhoto then 724 | begin 725 | LINE.Debug := True; 726 | LogUtil.Add( 'LINE-Photo', 'LINE'); 727 | LogUtil.Add( FileURL, 'LINE'); 728 | LINE.SendImage(LINE.UserID, FileURL); 729 | LogUtil.Add( LINE.ResultText, 'LINE'); 730 | end; 731 | 732 | if SendRichContent then 733 | begin 734 | LogUtil.Add( 'LINE-Rich Content', 'LINE'); 735 | LINE.Push(line.UserID, RichContent, True); 736 | LogUtil.Add(LINE.ResultText, 'LINE-Rich'); 737 | end; 738 | 739 | LogChat(LINE_CHANNEL_ID, Carik.GroupChatID, Carik.GroupName, 740 | Carik.UserID, Carik.UserName, Carik.FullName, Text, SimpleBOT.SimpleAI.ResponseText.Text, Carik.IsGroup, True); 741 | Analytics('line', SimpleBOT.SimpleAI.IntentName, Text, 'ln-' + Carik.UserID); 742 | //Response.Content := 'OK'; 743 | end; 744 | 745 | 746 | 747 | end. 748 | -------------------------------------------------------------------------------- /public_html/carik/files/word-nonstandard.txt: -------------------------------------------------------------------------------- 1 | [base] 2 | abjat=abjad 3 | abrasi=aberasi 4 | abreg=abrek 5 | absorsi=absorpsi 6 | accu=aki 7 | adap=adab 8 | adegio=adagio 9 | adek=adik 10 | adesi=adhesi 11 | aditorium=auditorium 12 | admin=administrator 13 | adpokat=advokat 14 | advent=adven 15 | adzan=azan 16 | afdol=afdal 17 | agamis=agamais 18 | agent=agen 19 | ajeg=ajek 20 | ajektif=adjektif 21 | ajimat=azimat 22 | akherat=akhirat 23 | akhlaq=akhlak 24 | akikah=akekah 25 | aksesoris=aksesori 26 | akte=akta 27 | aktifis=aktivis 28 | aktifitas=aktivitas 29 | aktip=aktif 30 | aktiv=aktif 31 | aktive=aktif 32 | aktuil=aktual 33 | akuntan=akutan 34 | akupuntur=akupunktur 35 | akutansi=akuntansi 36 | al-qur'an=Alquran 37 | al-quran=Alquran 38 | alaram=alarm 39 | alenia=alinea 40 | alfa=alpa 41 | alinia=alinea 42 | aliyah=aliah 43 | alloh=Allah 44 | almari=lemari 45 | almunium=aluminium 46 | alpha=alfa 47 | alpokat=avokad 48 | alpukat=avokad 49 | alternatip=alternatif 50 | alumunium=aluminium 51 | amandemen=amendemen 52 | amben=ambin 53 | ambeyen=ambeien 54 | ambulan=ambulans 55 | ambulance=ambulans 56 | amien=amin 57 | amirulhaj=amirulhaji 58 | amoniak=amonia 59 | amper=ampere 60 | amphibi=amfibi 61 | ampibi=amfibi 62 | analisa=analisis 63 | anestesia=anestesi 64 | anggauta=anggota 65 | angpao=angpau 66 | anoda=anode 67 | ansambel=ensambel 68 | antalogi=antologi 69 | antene=antena 70 | antri=antre 71 | antrian=antrean 72 | anugrah=anugerah 73 | apapun=apa pun 74 | aparatur=aparat 75 | apem=apam 76 | aplus=aplaus 77 | apostrop=apostrof 78 | apotik=apotek 79 | aqil=akil 80 | aquades=akuades 81 | aquarium=akuarium 82 | aquatik=akuatik 83 | arbiter=arbitrer 84 | aritmatika=aritmetika 85 | arkheolog=arkeolog 86 | arkheologi=arkeologi 87 | artifak=artefak 88 | asal-muasal=muasal 89 | aseli=asli 90 | aseptor=akseptor 91 | asesori=aksesori 92 | ashar=asar 93 | asik=asyik 94 | astaghfirullah=astagfirullah 95 | astronot=astronaut 96 | atheis=ateis 97 | atlit=atlet 98 | atmosfir=atmosfer 99 | atmosphere=atmosfer 100 | atret=ateret 101 | audiens=audiensi 102 | auliya=aulia 103 | autobiografi=otobiografi 104 | automatic=otomatis 105 | automatis=otomatis 106 | azas=asas 107 | azasi=asasi 108 | azaz=asas 109 | azhab=azab 110 | azhar=Asar 111 | babtis=baptis 112 | baek=baik 113 | bahwasannya=bahwasanya 114 | bakmie=bakmi 115 | bakpau=bakpao 116 | balance=balans 117 | bale=balai 118 | baligh=balig 119 | balpoin=bolpoin 120 | balsem=balsam 121 | bandrol=banderol 122 | bangker=bungker 123 | bapakda=bapanda 124 | bapaknda=bapanda 125 | baqa=baka 126 | barigade=barikade 127 | barzah=barzakh 128 | baso=bakso 129 | batalyon=batalion 130 | batere=baterai 131 | baterei=baterai 132 | bathil=batil 133 | bathin=batin 134 | batre=baterai 135 | bazaar=bazar 136 | beaya=biaya 137 | bedug=beduk 138 | belangko=blangko 139 | belender=blender 140 | belepot=gelepot 141 | belom=belum 142 | beludru=beledu 143 | bemper=bumper 144 | bengap=bengep 145 | bengkoang=bengkuang 146 | bengkowang=bengkuang 147 | bensol=benzol 148 | bergadang=begadang 149 | bergajul=bargajul 150 | berjanji=barzanj 151 | berlepotan=gelepotan 152 | berpetualang=bertualang 153 | berserta=beserta 154 | berterbangan=beterbangan 155 | berternak=beternak 156 | bh=beha 157 | bhayangkara=bayangkara 158 | bhiku=biksu 159 | bhuana=buana 160 | biarpet=byarpet 161 | bienale=bienial 162 | biennale=bienial 163 | bilyar=biliar 164 | bilyun=biliun 165 | binatu=benatu 166 | binatu=penatu 167 | biosfir=biosfer 168 | birahi=berahi 169 | bis=bus 170 | bisep=biseps 171 | blacu=belacu 172 | blanko=blangko 173 | blantika=belantika 174 | blokir=blokade 175 | bloon=beloon 176 | bolpen=bolpoin 177 | bolpoint=bolpoin 178 | bombon=bobon 179 | bonafid=bonafide 180 | bongkok=bungkuk 181 | boss=bos 182 | boulevard=bulevar 183 | bowling=boling 184 | braile=braille 185 | brandal=berandal 186 | brangkas=brankas 187 | breidel=bredel 188 | brengsek=berengsek 189 | brewok=bewok 190 | bridel=bredel 191 | brigade=barikade 192 | brilyan=brilian 193 | brokad=brokat 194 | bromocorah=bramacorah 195 | bronkitis=bronkhitis 196 | buda=Buddha 197 | budeg=budek 198 | budget=bujet 199 | budha=Buddha 200 | bumiputera=bumiputra 201 | bungalow=bungalo 202 | bur=bor 203 | busyet=buset 204 | cabay=cabai 205 | cabe=cabai 206 | cacad=cacat 207 | cafetaria=kafetaria 208 | cape=capai 209 | capek=capai 210 | cathering=katering 211 | cedal=cadel 212 | celos=celus 213 | cemilan=camilan 214 | cendikia=cendekia 215 | cendikiawan=cendekiawan 216 | cengkeh=cengkih 217 | cengkram=cengkeram 218 | cengkrama=cengkerama 219 | centigram=sentigram 220 | centimeter=sentimeter 221 | central=sentral 222 | ceret=cerek 223 | ceritera=cerita 224 | chlor=klor 225 | cicak=cecak 226 | cidera=cedera 227 | cigaret=sigaret 228 | cinderamata=cenderamata 229 | cingcong=cincong 230 | clash=kles 231 | clien=klien 232 | closet=kloset 233 | club=klab 234 | clurit=celurit 235 | cockpit=kokpit 236 | cocktail=koktail 237 | coklat=cokelat 238 | combro=comro 239 | cru=kru 240 | cumulus=kumulus 241 | da'i=dai 242 | da’i=dai 243 | da’wah=dakwah 244 | dajjal=dajal 245 | daptar=daftar 246 | dealer=diler 247 | debet=debit 248 | debetur=debitur 249 | debitur=debitor 250 | defiasi=deviasi 251 | degresi=digresi 252 | degub=degup 253 | dekoratip=dekoratif 254 | dekrit=dekret 255 | deodorant=deodoran 256 | depo=depot 257 | depolitisir=depolitisasi 258 | deputy=deputi 259 | design=desain 260 | despenser=dispenser 261 | destilasi=distilasi 262 | detektip=detektif 263 | detel=detail 264 | deterjen=detergen 265 | detil=detail 266 | deviden=dividen 267 | dharma=darma 268 | dhohir=lahir 269 | dhoif=daif 270 | dhu'afa=duafa 271 | dhuafa=duafa 272 | dhuha=duha 273 | dhuhur=zhuhur 274 | dhuhur=zuhur 275 | diagnosa=diagnosis 276 | diagnose=diagnosis 277 | diantaranya=di antaranya 278 | dimana=di mana 279 | dimanapun=di mana pun 280 | dioda=diode 281 | dipungkiri=dimungkiri 282 | disain=desain 283 | disainer=desainer 284 | disco=disko 285 | diserse=desersi 286 | disersi=desersi 287 | disini=di sini 288 | diskotik=diskotek 289 | diskripsi=deskripsi 290 | ditambahin=ditambahkan 291 | do'a=doa 292 | dollar=dolar 293 | domain=domein 294 | donatur=donator 295 | dopping=doping 296 | dos=dus 297 | dosin=lusin 298 | dozen=lusin 299 | draft=draf 300 | dramatisir=dramatisasi 301 | dramben=drumben 302 | dumping=damping 303 | duren=durian 304 | dzat=zat 305 | dzikir=zikir 306 | dzuhur=zuhur 307 | efektifitas=efektivitas 308 | efektip=efektif 309 | efektive=efektif 310 | eksebisi=ekshibisi 311 | eksem=eksim 312 | eksibisi=ekshibisi 313 | eksim=eksem 314 | eksport=ekspor 315 | ekstrim=ekstrem 316 | ekstrovert=ekstrover 317 | ekwivalen=ekuivalen 318 | elektroda=elektrode 319 | elip=elips 320 | elit=elite 321 | email=e-mail 322 | empek-empek=pempek 323 | eneg=enek 324 | engine=enjin 325 | ensiklopedia=ensiklopedi 326 | epektif=efektif 327 | epektip=efektif 328 | ephos=epos 329 | episod=episode 330 | equivalen=ekuivalen 331 | erobatik=aerobatik 332 | esen=esens 333 | esense=esens 334 | essai=esai 335 | essay=esai 336 | ethanol=etanol 337 | exim=eksem 338 | export=ekspor 339 | extra=ekstra 340 | extrim=ekstrem 341 | facsimil=faksimili 342 | faham=paham 343 | fak=vak 344 | faksimil=faksimile 345 | faksimil=faksimili 346 | faksimili=faksimile 347 | faksinasi=vaksinasi 348 | fakum=vakum 349 | falid=valid 350 | familiar=familier 351 | famplet=pamflet 352 | faqih=fakih 353 | farmakop=farmakope 354 | fas=vas 355 | faseh=fasih 356 | fasip=pasif 357 | faximil=faksimili 358 | february=Februari 359 | feminim=feminin 360 | ferri=feri 361 | fery=feri 362 | fihak=pihak 363 | fikir=pikir 364 | filosof=filsuf 365 | filsof=filsuf 366 | finish=finis 367 | fitoksoit=fitotoksoid 368 | foklor=folklor 369 | formil=formal 370 | fotosintesa=fotosintesis 371 | fotosintetis=fotosintesis 372 | frasa=frase 373 | frase=frasa 374 | frekwensi=frekuensi 375 | frigit=frigid 376 | fron=front 377 | frustasi=frustrasi 378 | furniture=furnitur 379 | galaktose=galaktosa 380 | galery=galeri 381 | galleri=galeri 382 | gamma=game 383 | gandewo=gandewa 384 | garebeg=garebek 385 | gasal=gazal 386 | geladi=gladi 387 | gelo=gila 388 | gendewa=gandewa 389 | geneaologi=genealogi 390 | geneologi=genealogi 391 | genius=jenius 392 | genteng=genting 393 | gep=gap 394 | gepok=kepok 395 | gerejani=gerejawi 396 | gerobag=gerobak 397 | geyser=geiser 398 | ghaib=gaib 399 | ghoib=gaib 400 | gip=gips 401 | gisi=gizi 402 | gladi=geladi 403 | gladibersih=geladi bersih 404 | glamour=glamor 405 | glondong=gelondong 406 | glosary=glosarium 407 | glukoma=glaukoma 408 | glukose=glukosa 409 | goa=gua 410 | goncang=guncang 411 | gono-gini=gana-gini 412 | grameh=gurami 413 | grebeg=garebek 414 | grebek=gerebek 415 | greget=gereget 416 | grendel=gerendel 417 | gria=griya 418 | grogol=gerogol 419 | gross=gros 420 | gubug=gubuk 421 | gudek=gudeg 422 | gulabit=bitgula 423 | gurameh=gurami 424 | guyub=guyup 425 | hadist=hadis 426 | hakekat=hakikat 427 | hal-ihwal=hal-hal 428 | handaitaulan=handaitulan 429 | handal=andal 430 | hapal=hafal 431 | harafiah=harfiah 432 | hektar=hektare 433 | hembus=embus 434 | hempas=empas 435 | hentak=entak 436 | herbivora=herbivor 437 | hetrogen=heterogen 438 | hidrolis=hidraulis 439 | higiena=higiene 440 | himbau=imbau 441 | himpit=impit 442 | hingar-bingar=ingar-bingar 443 | hingar=ingar 444 | hipermetri=hipermetropia 445 | hipotesa=hipotesis 446 | hipotik=hipotek 447 | hipovitaminose=hipovitaminosis 448 | hirarki=hierarki 449 | hiroglif=hieroglif 450 | hisap=isap 451 | hobby=hobi 452 | holistic=holistis 453 | holistik=holistis 454 | honocoroko=hanacaraka 455 | horden=gorden 456 | hordeng=gorden 457 | horison=horizon 458 | hurup=huruf 459 | husada=usada 460 | hutang=utang 461 | hybrida=hibrida 462 | hygiene=higiene 463 | hymne=himne 464 | i’tibar=iktibar 465 | i’tikaf=iktikaf 466 | ibtidaiyah=ibtidaiah 467 | iddah=idah 468 | idial=ideal 469 | idiil=ideal 470 | idiologi=ideologi 471 | ihlas=ikhlas 472 | ijasah=ijazah 473 | ijin=izin 474 | ijma’=ijmak 475 | ikhwal=ihwal 476 | iklas=ikhlas 477 | illusi=ilusi 478 | imajinasi=imaginasi 479 | imel=e-mail 480 | import=impor 481 | incognito=inkognito 482 | income=inkam 483 | indera=indra 484 | indra=indera 485 | influensa=influenza 486 | influinza=influenza 487 | inpus=infus 488 | instink=insting 489 | insyaf=insaf 490 | intel=intelijen 491 | intelegensi=inteligensi 492 | intelejensi=intelegensi 493 | inteligen=intelijen 494 | inten=intens 495 | intercontinental=interkontinental 496 | interest=interes 497 | intermezo=intermeso 498 | internist=internis 499 | interograsi=interogasi 500 | interospeksi=introspeksi 501 | interplasi=interpelasi 502 | interprestasi=interpretasi 503 | introvert=introver 504 | intrupsi=interupsi 505 | inventarisir=inventarisasi 506 | inzet=inset 507 | ionosfir=ionosfer 508 | iradah=iradat 509 | irasionil=irasional 510 | irodah=iradat 511 | irrasional=irasional 512 | islamiyah=Islamiah 513 | isra’=israk 514 | isteri=istri 515 | istighfar=istigfar 516 | istinja’=istinjak 517 | istiqomah=istikamah 518 | itali=Italia 519 | itikad=iktikad 520 | izajah=ijazah 521 | jadah=juadah 522 | jadual=jadwal 523 | jaduwal=jadwal 524 | jaelangkung=jalangkung 525 | jagad=jagat 526 | jahil=jail 527 | jahiliyah=jahiliah 528 | jailangkung=jalangkung 529 | jaman=zaman 530 | jarik=jarit 531 | jeep=jip 532 | jejer=jajar 533 | jemaah=jamaah 534 | jemaat=jamaah 535 | jembel=gembel 536 | jenasah=jenazah 537 | jendral=jenderal 538 | jenius=genius 539 | jep=jip 540 | jerembab=jerembap 541 | jerembap=jerembab 542 | jerigen=jeriken 543 | jina=zina 544 | jiujitsu=jujitsu 545 | jizim=jisim 546 | jogging=joging 547 | joint=join 548 | jomblo=jomlo 549 | jor-joran=jorjoran 550 | jubilum=jubileum 551 | jum'at=Jumat 552 | jumawa=jemawa 553 | jungtur=junktur 554 | jus=juz 555 | justeru=justru 556 | ka’bah=kakbah 557 | kaabah=kakbah 558 | kaburasi=karburasi 559 | kaburator=karburator 560 | kadaluarsa=kedaluwarsa 561 | kadaluwarsa=kedaluwarsa 562 | kaedah=kaidah 563 | kaffah=kafah 564 | kahyangan=kayangan 565 | kakatua=kakaktua 566 | kaleidioskop=kaleidoskop 567 | kalkarim=kalkarium 568 | kamboja=kemboja 569 | kameraman=kamerawan 570 | kameramen=kamerawan 571 | kamuplase=kamuflase 572 | kangguru=kanguru 573 | kangker=kanker 574 | kantung=kantong 575 | kaos=kaus 576 | karir=karier 577 | karna=karena 578 | kasep=kasip 579 | kastil=kastel 580 | katagori=kategori 581 | kataketis=katekis 582 | katalepsia=katalepsi 583 | katalisa=katalisis 584 | kate=katai 585 | katholik=Katolik 586 | katoda=katode 587 | katring=katering 588 | keburu=terburu 589 | kecibeling=kejibeling 590 | kecoak=kacoak 591 | kedaluarsa=kedaluwarsa 592 | kedele=kedelai 593 | kekawin=kakawin 594 | kelakatu=kelekatu 595 | kelenger=kelengar 596 | kelep=klep 597 | kemana=ke mana 598 | kempes=kempis 599 | kenalpot=knalpot 600 | kendor=kendur 601 | kenop=knop 602 | kerapan=karapan 603 | kerawitan=karawitan 604 | kerdip=kedip 605 | kerdus=kardus 606 | kerjasama=kerja sama 607 | kerol=krol 608 | kesturi=kasturi 609 | kesumah=kesuma 610 | ketapel=katapel 611 | ketawa=tertawa 612 | ketemu=bertemu 613 | ketimun=mentimun 614 | kharisma=karisma 615 | kharismatik=karismatik 616 | khaul=kaul 617 | khayangan=kayangan 618 | khutbah=khotbah 619 | klar=kelar 620 | klemak-klemek=kelemak-kelemek 621 | klenger=kelengar 622 | klengkeng=kelengkeng 623 | klenik=kelenik 624 | kleptomani=kleptomania 625 | klop=kelop 626 | klorofil=kloropil 627 | kloter=keloter 628 | kluwak=keluak 629 | kluwih=keluih 630 | knop=kenop 631 | koboy=koboi 632 | kocar-kacir=kucar-kacir 633 | kolomnis=kolumnis 634 | komersil=komersial 635 | komfirmasi=konfirmasi 636 | komoditi=komoditas 637 | komplit=komplet 638 | konggres=kongres 639 | kongkow=kongko 640 | kongkret=konkret 641 | kongkrit=konkret 642 | konkrit=konkret 643 | konsekwen=konsekuen 644 | konsleting=korsleting 645 | kontinyu=kontinu 646 | koor=kor 647 | koordinir=koordinasi 648 | kopor=koper 649 | korden=gorden 650 | korma=kurma 651 | korp=korps 652 | kosmonot=kosmonaut 653 | kram=keram 654 | kramat=keramat 655 | kreatifitas=kreativitas 656 | kreatip=kreatif 657 | kreative=kreatif 658 | kremi=keremi 659 | kresek=keresek 660 | kretek=keretek 661 | krew=kru 662 | kridit=kredit 663 | krucil=kerucil 664 | kulintang=kolintang 665 | kumplit=komplet 666 | kuno=kuna 667 | kurnia=karunia 668 | kusen=kosen 669 | kusuma=kesuma 670 | kutilang=ketilang 671 | kwaci=kuaci 672 | kwalitas=kualitas 673 | kwalitet=kualitas 674 | kwantitas=kuantitas 675 | kwartal=kuartal 676 | kwitangsi=kuitansi 677 | kwitansi=kuitansi 678 | kwota=kuota 679 | kyai=kiai 680 | la'nat=laknat 681 | laba-laba=labah-labah 682 | lajim=lazim 683 | lamtorogung=lamtaragung 684 | lapal=lafal 685 | lasim=lazim 686 | lasykar=laskar 687 | laveransir=leveransir 688 | ledeng=leding 689 | legalisir=legalisasi 690 | legenda=legende 691 | lembab=lembap 692 | leukimia=leukemia 693 | levender=lavendel 694 | liat=lihat 695 | limfe=limfa 696 | limpha=limpa 697 | linier=linear 698 | literal=litoral 699 | liver=lever 700 | lobang=lubang 701 | loby=lobi 702 | lohor=zhuhur 703 | lokalisir=lokalisasi 704 | longmarch=longmars 705 | lontang-lantung=luntang-lantung 706 | losin=lusin 707 | lotere=lotre 708 | luwak=luak 709 | lux=luks 710 | ma'af=maaf 711 | ma’af=maaf 712 | ma’fum=mafhum 713 | ma’rifat=makrifat 714 | ma’ruf=makruf 715 | maag=mag 716 | mabok=mabuk 717 | madukoro=madukara 718 | madzab=mazhab 719 | maesa=mahesa 720 | mafum=mafhum 721 | maghrib=magrib 722 | mahabarata=Mahabharata 723 | mahapengasih=Maha Pengasih 724 | mahardhika=mahardika 725 | mahfudz=mahfuz 726 | mahluk=makhluk 727 | mahnet=magnet 728 | maisena=maizena 729 | makcomblang=mak comblang 730 | makdum=makhdum 731 | mala-praktek=malapraktik 732 | malpraktek=malapraktik 733 | malpraktik=malapraktik 734 | mampet=mampat 735 | manager=manajer 736 | mandeg=mandek 737 | manekin=maneken 738 | mangkok=mangkuk 739 | mantab=mantap 740 | mantera=mantra 741 | manuskrif=manuskrip 742 | maqam=makam 743 | maqom=makam 744 | marathon=maraton 745 | margarine=margarin 746 | marjinal=marginal 747 | mas=emas 748 | masal=massal 749 | mashur=masyhur 750 | matematik=matematika 751 | materai=meterai 752 | mbalelo=mbalela 753 | mebeler=mebel 754 | melody=melodi 755 | mencolok=menyolok 756 | mendam=mandam 757 | mendem=mandam 758 | mentari=matahari 759 | menterapkan=menerapkan 760 | menterjemahkan=menerjemahkan 761 | mentertawakan=menertawakan 762 | menthol=mentol 763 | menyan=kemenyan 764 | menyuci=mencuci 765 | meram=merem 766 | merk=merek 767 | merkurokrum=merkurokrom 768 | mesjid=masjid 769 | mess=mes 770 | methanol=metanol 771 | metoda=metode 772 | metrei=meterai 773 | mi’raj=mikraj 774 | mie=mi 775 | migren=migrain 776 | mikroba=mikrobe 777 | milyader=miliarder 778 | milyar=miliar 779 | milyoner=miliuner 780 | milyuner=miliuner 781 | miopi=miopia 782 | missi=misi 783 | mithos=mitos 784 | miyop=miop 785 | mobilisir=mobilisasi 786 | moderen=modern 787 | monarkhi=monarki 788 | monopause=menopause 789 | monotheis=monoteis 790 | monotype=monotipe 791 | montage=montase 792 | moril=moral 793 | moto=motto 794 | mozaik=mosaik 795 | mpu=empu 796 | mu'jizat=mukjizat 797 | mu’jizat=mukjizat 798 | muadzin=muazin 799 | muamalah=muamalat 800 | mubaligh=mubalig 801 | mubalighoh=mubaligat 802 | mucikari=muncikari 803 | mukjijat=mukjizat 804 | mummi=mumi 805 | muqaddimah=mukadimah 806 | muqadimah=mukadimah 807 | mursid=mursyid 808 | mushala=musala 809 | musholah=musala 810 | musholla=musala 811 | musium=museum 812 | mustika=mestika 813 | musyafir=musafir 814 | nadar=nazar 815 | nadzar=nazar 816 | nafas=napas 817 | nahas=naas 818 | nahkoda=nakhoda 819 | nakoda=nakhoda 820 | nampak=tampak 821 | narkotika=narkotik 822 | nasehat=nasihat 823 | negatip=negatif 824 | negoisasi=negosiasi 825 | negri=negeri 826 | neko-neko=neka-neka 827 | nenas=nanas 828 | neo-kolonialisme=neokolonialisme 829 | netralisir=netralisasi 830 | netting=neting 831 | netto=neto 832 | ni'mat=nikmat 833 | nipas=nifas 834 | nomaden=nomad 835 | nomer=nomor 836 | non-aktif=nonaktif 837 | nonsen=nonsens 838 | nopember=November 839 | notulen=notula 840 | obrak-abrik=ubrak-abrik 841 | obyek=objek 842 | obyektif=objektif 843 | oditorium=auditorium 844 | okulele=ukulele 845 | omset=omzet 846 | ongseng=gongseng 847 | oplet=opelet 848 | opostrop=apostrof 849 | orange=oranye 850 | orangtua=orang tua 851 | orchestra=orkestra 852 | organisir=organisasi 853 | orisinil=orisinal 854 | orkhestra=orkestra 855 | oseng-oseng=gongseng 856 | osmosis=osmose 857 | otentik=autentik 858 | otobiografi=autobiografi 859 | otodidak=autodidak 860 | otopsi=autopsi 861 | otto=oto 862 | pacet=pacat 863 | padepokan=pedepokan 864 | padri=paderi 865 | palem=palm 866 | pamfelet=pamflet 867 | panembahan=penembahan 868 | pangkreas=pankreas 869 | panili=vanili 870 | panitra=panitera 871 | panu=panau 872 | paradox=paradoks 873 | paragoge=parogog 874 | paramedik=paramedis 875 | parasit=parasut 876 | pasca-panen=pascapanen 877 | pasip=pasif 878 | pasive=pasif 879 | pasport=paspor 880 | patent=paten 881 | pateri=patri 882 | patriakat=patriarkat 883 | patrilinial=patrilineal 884 | paviliyun=paviliun 885 | pavilyun=paviliun 886 | pebruari=Februari 887 | pedes=pedas 888 | pelaminan=pelamin 889 | peliara=pelihara 890 | penasehat=penasihat 891 | pendopo=pendapa 892 | pengrajin=perajin 893 | perduli=peduli 894 | pernis=vernis 895 | petay=petai 896 | pete=petai 897 | philipina=Filipina 898 | phobi=fobi 899 | phobia=fobia 900 | photo=foto 901 | piara=pelihara 902 | piranti=peranti 903 | pirsawan=pemirsa 904 | piyama=piama 905 | plat=flat 906 | plesetan=pelesetan 907 | plesir=pelesir 908 | plet=flat 909 | pleton=peleton 910 | plintir=pelintir 911 | plonco=pelonco 912 | plontos=pelontos 913 | polio=folio 914 | polpen=bolpoin 915 | pondasi=fondasi 916 | popular=populer 917 | porcelain=porselen 918 | porselain=porselen 919 | praktek=praktik 920 | profinsi=provinsi 921 | project=proyek 922 | projek=proyek 923 | proklamir=proklamasi 924 | propinsi=provinsi 925 | pungkir=mungkir 926 | putera=putra 927 | qalam=kalam 928 | qasidah=kasidah 929 | qodariyah=kadariah 930 | qodi=kadi 931 | qodiriyah=Kadiriah 932 | qolam=kalam 933 | qolbu=kalbu 934 | qomariyah=Kamariah 935 | qomat=kamat 936 | qona’ah=kanaah 937 | qori=qari 938 | qoriah=qariah 939 | qosidah=kasidah 940 | qunut=kunut 941 | qur’an=Quran 942 | quraisy=Kuraisy 943 | rajia=razia 944 | raka'at=rakaat 945 | raka’at=rakaat 946 | ramadhan=Ramadan 947 | rangking=ranking 948 | rangsel=ransel 949 | ranzel=ransel 950 | rapal=lafal 951 | rapih=rapi 952 | rapor=rapot 953 | raport=rapor 954 | rapot=rapor 955 | rasia=razia 956 | rasialist=rasialis 957 | rasionil=rasional 958 | real=riil 959 | realisir=realisasi 960 | reamur=Reaumur 961 | rebo=Rabu 962 | regim=rezim 963 | rejeki=rezeki 964 | rejeki=rizki 965 | rejim=rezim 966 | reka'at=rakaat 967 | rekaat=rakaat 968 | rekruit=rekrut 969 | relif=relief 970 | rembug=rembuk 971 | renaisan=renaisans 972 | renaisance=renaisans 973 | rengking=ranking 974 | reptil=reptilia 975 | reservoir=reservoar 976 | resiko=risiko 977 | respon=respons 978 | restauran=restoran 979 | restaurant=restoran 980 | resum=resume 981 | reumatik=rematik 982 | rezeki=rizki 983 | rezki=rezeki 984 | ridho=rida 985 | riil=real 986 | rilai=relai 987 | rile=relai 988 | riski=rizki 989 | ritme=ritma 990 | ritsluiting=ritsleting 991 | rizki=rezeki 992 | rizqi=rezeki 993 | rizqi=rizki 994 | robah=ubah 995 | roboh=rubuh 996 | rocker=roker 997 | roh=ruh 998 | rohaniawan=ruhaniwan 999 | romadhon=Ramadan 1000 | romadlon=Ramadan 1001 | romo=rama 1002 | romusha=romusa 1003 | rong-rong=rongrong 1004 | ronsen=rontgen 1005 | route=rute 1006 | rubah=ubah 1007 | ruku’=rukuk 1008 | sa’i=sai 1009 | sahadat=syahadat 1010 | sahid=syahid 1011 | sahwat=syahwat 1012 | sakharin=sakarin 1013 | saklar=sakelar 1014 | salesma=selesma 1015 | samadi=semadi 1016 | sambel=sambal 1017 | sambrero=sombrero 1018 | sanawiyah=sanawiah 1019 | sangkalan=sengkalan 1020 | sangsi=sanksi 1021 | sanjak=sajak 1022 | sanksi=sangsi 1023 | sansekerta=Sanskerta 1024 | saos=saus 1025 | saparila=sarsaparila 1026 | saplemen=suplemen 1027 | sarap=saraf 1028 | sariawan=seriawan 1029 | sate=satai 1030 | satire=satir 1031 | score=skor 1032 | sebab-musabab=musabab 1033 | seign=sein 1034 | sejarahwan=sejarawan 1035 | sekedar=sekadar 1036 | sekering=sekring 1037 | sekertaris=sekretaris 1038 | sekolastik=skolastik 1039 | sekor=skor 1040 | sekores=skors 1041 | sekors=skors 1042 | seksama=saksama 1043 | seksuil=seksual 1044 | sekta=sekte 1045 | sekterian=sektarian 1046 | sekuadron=eskadron 1047 | sekuler=sekular 1048 | selinder=silinder 1049 | selulose=selulosa 1050 | semanda=semenda 1051 | sembrono=sembrana 1052 | semedi=semadi 1053 | sempoa=swipoa 1054 | sen=sein 1055 | sendal=sandal 1056 | senggama=sanggama 1057 | senikdok=sinekdoke 1058 | senopati=senapati 1059 | sense=sinse 1060 | sentausa=sentosa 1061 | sentimentil=sentimental 1062 | sentra=sentral 1063 | sepakbor=sepatbor 1064 | sepanduk=spanduk 1065 | sepesial=spesial 1066 | sepesies=spesies 1067 | sepionase=spionase 1068 | sepiritus=spiritus 1069 | sepirtus=spiritus 1070 | sepon=spons 1071 | sepre=seprai 1072 | seprei=seprai 1073 | sere=serai 1074 | sereh=serai 1075 | sertipikat=sertifikat 1076 | seruling=suling 1077 | seruni=serunai 1078 | service=servis 1079 | setansa=stanza 1080 | seterika=setrika 1081 | setriker=striker 1082 | sex=seks 1083 | seyogyanya=seyogianya 1084 | shaf=saf 1085 | shalat=salat 1086 | shampo=sampo 1087 | shampoo=sampo 1088 | she=syekh 1089 | shogun=syogun 1090 | sholat=salat 1091 | siapapun=siapa pun 1092 | sie=seksi 1093 | sign=sein 1094 | silahkan=silakan 1095 | silaturohmi=silaturahmi 1096 | silaturrahmi=silaturahmi 1097 | simple=simpel 1098 | sinagog=sinagoge 1099 | sindrome=sindrom 1100 | sinkope=sinkop 1101 | sinse=sengse 1102 | sintesa=sintesis 1103 | sintese=sintesis 1104 | sintesis=sintetis 1105 | siphilis=sifilis 1106 | sipilis=sifilis 1107 | sipoa=swipoa 1108 | sirik=syirik 1109 | sirine=sirene 1110 | sirop=sirup 1111 | sirup=sirop 1112 | sistim=sistem 1113 | sitar=ziter 1114 | siter=ziter 1115 | siwa=Syiwa 1116 | skholastik=skolastik 1117 | skop=sekop 1118 | skore=skor 1119 | skorsing=skors 1120 | sky=ski 1121 | slank=slang 1122 | slendro=selendro 1123 | sleng=slang 1124 | slenk=slang 1125 | slinder=silinder 1126 | smash=smes 1127 | sobat=sahabat 1128 | sodakoh=sedekah 1129 | sodaqoh=sedekah 1130 | sofball=sofbal 1131 | softball=sofbal 1132 | sokhib=sahib 1133 | sokoguru=sakaguru 1134 | solenoid=solenoide 1135 | sop=sup 1136 | sopmberero=sombrero 1137 | sorban=serban 1138 | sorga=surga 1139 | soup=sop 1140 | souvenir=suvenir 1141 | spagetti=spageti 1142 | spagheti=spageti 1143 | spakbor=sepatbor 1144 | spakbort=sepatbor 1145 | special=spesial 1146 | species=spesies 1147 | speedboat=spitbot 1148 | speedbot=spitbot 1149 | sping=sfing 1150 | spink=sfing 1151 | spinx=sfing 1152 | spirituil=spiritual 1153 | spon=spons 1154 | spor=sepur 1155 | sprai=seprai 1156 | sprint=sprin 1157 | spritus=spiritus 1158 | spur=sepur 1159 | sreg=srek 1160 | srigala=serigala 1161 | stagen=setagen 1162 | stand=stan 1163 | standard=standar 1164 | standarisasi=standardisasi 1165 | standart=standar 1166 | stansa=stanza 1167 | stater=starter 1168 | stereotipe=stereotip 1169 | sticker=stiker 1170 | stip=setip 1171 | stir=setir 1172 | stock=stok 1173 | stratejik=strategis 1174 | strawberi=stroberi 1175 | strawberry=stroberi 1176 | strawbery=stroberi 1177 | stress=stres 1178 | stricker=striker 1179 | strip=setrip 1180 | strok=stroke 1181 | subsidair=subsider 1182 | subtansi=substansi 1183 | subtitusi=substitusi 1184 | subyek=subjek 1185 | sudet=sodet 1186 | suhada=syuhada 1187 | suiter=sweter 1188 | sukur=syukur 1189 | sundel=sundal 1190 | sunnah=sunah 1191 | sup=sop 1192 | superman=supermen 1193 | supermasi=supremasi 1194 | supir=sopir 1195 | suplement=suplemen 1196 | sur=syur 1197 | surat=surah 1198 | survai=survei 1199 | survay=survei 1200 | surve=survei 1201 | survey=survei 1202 | susastera=susastra 1203 | sutra=sutera 1204 | syafa’at=syafaat 1205 | syah=sah 1206 | syahdu=sahdu 1207 | syahit=syahid 1208 | syaiton=setan 1209 | syaraf=saraf 1210 | syarap=saraf 1211 | syareat=syariat 1212 | syarekat=syarikat 1213 | syeikh=syekh 1214 | syetan=setan 1215 | syi’ar=siar 1216 | syiar=siar 1217 | syrup=sirup 1218 | system=sistem 1219 | syubat=syubhat 1220 | syubkhat=syubhat 1221 | syurga=surga 1222 | ta’ala=taala 1223 | ta’zim=takzim 1224 | tabligh=tablig 1225 | tagen=setagen 1226 | tahiyat=tahiat 1227 | tahta=takhta 1228 | takjim=takzim 1229 | talek=talk 1230 | tamzil=tamsil 1231 | tangker=tanker 1232 | tape=tapai 1233 | tapelak=taplak 1234 | tapi=tetapi 1235 | taqwa=takwa 1236 | tarhim=tarkhim 1237 | tarkim=tarkhim 1238 | taruna=teruna 1239 | tataniaga=tata niaga 1240 | tatto=tato 1241 | taubat=tobat 1242 | tauco=taoco 1243 | tauge=taoge 1244 | taulada=teladan 1245 | tauladan=teladan 1246 | tawakkal=tawakal 1247 | taxi=taksi 1248 | team=tim 1249 | tehnik=teknik 1250 | tehnologi=teknologi 1251 | tekat=tekad 1252 | teke=tokek 1253 | tekek=tokek 1254 | tekhnik=teknik 1255 | tekhnologi=teknologi 1256 | telefon=telepon 1257 | telephone=telepon 1258 | telfon=telepon 1259 | telor=telur 1260 | telpon=telepon 1261 | temenggung=tumenggung 1262 | temugiring=temu giring 1263 | tentram=tenteram 1264 | teoritis=teoretis 1265 | tepekong=toapekong 1266 | terimakasih=terima kasih 1267 | terlanjur=telanjur 1268 | terlantar=telantar 1269 | terlentang=telentang 1270 | terong=terung 1271 | terpedo=torpedo 1272 | terpercaya=tepercaya 1273 | terperdaya=teperdaya 1274 | tersina=terzina 1275 | teruwelu=terwelu 1276 | tes=test 1277 | test=tes 1278 | thawaf=tawaf 1279 | theater=teater 1280 | theologi=teologi 1281 | thesis=tesis 1282 | thoriqoh=tarikat 1283 | thoriqot=tarikat 1284 | ticket=tiket 1285 | timun=mentimun 1286 | tipes=tifus 1287 | tips=tip 1288 | toge=taoge 1289 | toladan=teladan 1290 | tolerir=toleransi 1291 | tonel=tonil 1292 | topaz=topas 1293 | toples=stoples 1294 | tour=tur 1295 | touris=turis 1296 | tournamen=turnamen 1297 | trachome=trakom 1298 | tradisionil=tradisional 1299 | trakhom=trakom 1300 | trampil=terampil 1301 | trapo=trafo 1302 | trenggiling=tenggiling 1303 | trengginas=terengginas 1304 | tribun=tribune 1305 | trilyun=triliun 1306 | trinale=trienale 1307 | tripang=teripang 1308 | triplek=tripleks 1309 | triplex=tripleks 1310 | tritis=teritis 1311 | trofosfir=trofosfer 1312 | tromol=teromol 1313 | trophi=trofi 1314 | tropi=trofi 1315 | trotoir=trotoar 1316 | trubus=terubus 1317 | truwelu=terwelu 1318 | tsanawiyah=sanawiah 1319 | tungro=tungra 1320 | turnament=turnamen 1321 | tut=tuts 1322 | type=tipe 1323 | ukhrowi=ukhrawi 1324 | uneg-uneg=unek-unek 1325 | urin=urine 1326 | ustad=ustaz 1327 | ustadz=ustaz 1328 | ustadzah=ustazah 1329 | vacum=vakum 1330 | valentin=valentine 1331 | vampire=vampir 1332 | vanilli=vanili 1333 | varices=varises 1334 | varitas=varietas 1335 | vaskuler=vaskular 1336 | vegetarian=vegetaris 1337 | vermaks=vermak 1338 | vignet=vinyet 1339 | villa=vila 1340 | weker=beker 1341 | yudikatif=judikatif 1342 | yudisial=judisial 1343 | yudo=judo 1344 | yunior=junior 1345 | yurisdiksi=jurisdiksi 1346 | yuyitsu=jujitsu 1347 | zahir=lahir 1348 | zam-zam=zamzam 1349 | zarafah=jerapah 1350 | zerafah=jerapah 1351 | zhuhur=zuhur 1352 | zig-zag=zigzag 1353 | zigote=zigot 1354 | zinah=zina 1355 | zohir=lahir 1356 | zone=zona 1357 | zygot=zigot 1358 | 1359 | [gabungan] 1360 | akhirul kalam=akhirulkalam 1361 | al qur'an=Alquran 1362 | cap cai=capcai 1363 | drum band=drumben 1364 | foto copy=fotokopi 1365 | foto kopi=fotokopi 1366 | foto studio=studio foto 1367 | geladi resik=geladi bersih 1368 | inkar sunah=inkarsunah 1369 | kaca mata=kacamata 1370 | kakak tua=kakaktua 1371 | keji beling=kejibeling 1372 | kumpul kebo=kumpul kerbau 1373 | kung fu=kungfu 1374 | long march=longmars 1375 | mas kawin=maskawin 1376 | mass media=media massa 1377 | nina bobo=ninabobo 1378 | pas foto=pasfoto 1379 | pas photo=pasfoto 1380 | penghujan=hujan 1381 | radio aktif=radioaktif 1382 | saka guru=sakaguru 1383 | sedia kala=sediakala 1384 | serba aneka=serbaneka 1385 | serba neka=serbaneka 1386 | sosio drama=sosiodrama 1387 | suka cita=sukacita 1388 | tepa selira=tepaselira 1389 | tepo seliro=tepaselira 1390 | toa pekong=toapekong 1391 | ujian ulangan=ujian ulang --------------------------------------------------------------------------------