Caputchin
أدلة التكامل

أمثلة تكامل الواجهة

الأداة عنصر مخصّص قياسي، فتعمل في كل إطار عمل بلا غلاف لتثبيته. الشكل دائمًا نفسه: حمّل الحزمة مرة واحدة (التكامل على جانب العميل)، واعرض <caputchin-widget sitekey="cpt_pub_..."> داخل نموذجك، واقرأ حقل caputchin-token المخفي الذي تحقنه حين يجتاز الزائر التحدّي. وللعبة، استبدل بـ <caputchin-game ... game="caputchin/games/leaf-memory">.

الأمثلة أدناه لا تختلف إلا في صياغة كل إطار عمل وفي شذوذه الواحد الخاص بالعنصر المخصّص.

HTML عادي

يركب الحقل المحقون مع POST نموذج عادي، فلا شيء لتوصيله:

<script src="https://cdn.jsdelivr.net/npm/@caputchin/widget@3/dist/widget.js"></script>

<form action="/contact" method="POST">
  <input name="email" type="email" required />
  <caputchin-widget sitekey="cpt_pub_..."></caputchin-widget>
  <button type="submit">Send</button>
</form>

React

استورد مرة واحدة عند الإقلاع، ثم اقرأ الحقل من FormData عند الإرسال:

import "@caputchin/widget";

export function ContactForm() {
  async function handleSubmit(e) {
    e.preventDefault();
    const data = new FormData(e.currentTarget);
    await fetch("/api/contact", {
      method: "POST",
      headers: { "content-type": "application/json" },
      body: JSON.stringify({ email: data.get("email"), token: data.get("caputchin-token") }),
    });
  }

  return (
    <form onSubmit={handleSubmit}>
      <input name="email" type="email" required />
      <caputchin-widget sitekey="cpt_pub_..." />
      <button type="submit">Send</button>
    </form>
  );
}

إن استخدمت TypeScript مع React، فأعلِن العنصرين مرة واحدة كي يقبلهما JSX:

// caputchin.d.ts
import type { DetailedHTMLProps, HTMLAttributes } from "react";
declare module "react" {
  namespace JSX {
    interface IntrinsicElements {
      "caputchin-widget": DetailedHTMLProps<HTMLAttributes<HTMLElement> & { sitekey: string }, HTMLElement>;
      "caputchin-game": DetailedHTMLProps<HTMLAttributes<HTMLElement> & { sitekey: string; game?: string; games?: string }, HTMLElement>;
    }
  }
}

صيغة declare module "react" هذه خاصة بـ JSX الخاص بـ React. في TypeScript العادي يكون العنصران مجرّد HTMLElement ولا يحتاجان إعلانًا، وأطر العمل الأخرى أدناه تكتب أنواع العناصر المخصّصة بطريقتها الخاصة، فلا تحتاج هذه الكتلة إلا في مشروع React.

Vue

أخبِر مُجمِّع Vue بأن وسوم caputchin- عناصر مخصّصة، كي لا يحاول حلّها كمكوّنات:

// vite.config.js
export default {
  plugins: [vue({ template: { compilerOptions: { isCustomElement: (tag) => tag.startsWith("caputchin-") } } })],
};
<script setup>
import "@caputchin/widget";
function onSubmit(e) {
  const data = new FormData(e.target);
  // send data.get("caputchin-token") to your backend
}
</script>

<template>
  <form @submit.prevent="onSubmit">
    <input name="email" type="email" required />
    <caputchin-widget sitekey="cpt_pub_..."></caputchin-widget>
    <button type="submit">Send</button>
  </form>
</template>

Svelte

تعرض Svelte العناصر المخصّصة كما هي، بلا إعداد لازم:

<script>
  import "@caputchin/widget";
  function onSubmit(e) {
    const data = new FormData(e.currentTarget);
    // send data.get("caputchin-token") to your backend
  }
</script>

<form on:submit|preventDefault={onSubmit}>
  <input name="email" type="email" required />
  <caputchin-widget sitekey="cpt_pub_..."></caputchin-widget>
  <button type="submit">Send</button>
</form>

Angular

أضف CUSTOM_ELEMENTS_SCHEMA إلى الوحدة أو المكوّن المستقل كي يسمح Angular بالوسم المجهول، واستورد الحزمة مرة واحدة (في main.ts):

import { Component, CUSTOM_ELEMENTS_SCHEMA } from "@angular/core";
import "@caputchin/widget";

@Component({
  selector: "contact-form",
  schemas: [CUSTOM_ELEMENTS_SCHEMA],
  template: `
    <form (submit)="onSubmit($event)">
      <input name="email" type="email" required />
      <caputchin-widget sitekey="cpt_pub_..."></caputchin-widget>
      <button type="submit">Send</button>
    </form>
  `,
})
export class ContactFormComponent {
  onSubmit(e: Event) {
    const data = new FormData(e.target as HTMLFormElement);
    // send data.get("caputchin-token") to your backend
  }
}

Next.js

كود React نفسه يعمل. يُعرَض العنصر المخصّص كوسم فارغ أثناء العرض على الخادم ويترقّى على العميل بمجرّد تحميل الحزمة، فلا حاجة إلى معالجة خاصة عدا استيراد @caputchin/widget في مكوّن عميل (أو تحميل سكربت CDN بـ next/script).

انظر أيضًا

في هذه الصفحة