Hướng dẫn php oauth2 rest api example - ví dụ về api php oauth2

API REST là một phần lớn của Internet ngày nay. Một số trường hợp sử dụng hàng ngày của API REST là:

  • Lái xe phụ trợ của các ứng dụng web/ứng dụng di động một trang
  • Tích hợp các ứng dụng khác nhau để trao đổi dữ liệu và tự động hóa quy trình công việc
  • Cung cấp kênh liên lạc cho các phần khác nhau của kiến ​​trúc hướng dịch vụ phức tạp
  • Kết nối các thiết bị IoT.

Bảo mật API REST là rất cần thiết bởi vì API có thể phơi bày chức năng mạnh mẽ, quan trọng và hoàn toàn nguy hiểm trên Internet. Ví dụ: ứng dụng FinTech SaaS có thể cung cấp API cho phép bạn thao túng tài khoản ngân hàng của mình, thanh toán, chuyển tiền ra nước ngoài hoặc tải xuống thông tin nhạy cảm như báo cáo ngân hàng của bạn, địa chỉ cá nhân/tên/ssn.

Hầu hết các khung ứng dụng web cung cấp các công cụ để xây dựng API REST an toàn nhanh chóng bằng cách sử dụng các giải pháp tiêu chuẩn công nghiệp như JSON Web Token (JWT) và OAuth 2.0. Tuy nhiên, nó trả tiền để hiểu những gì nằm dưới mui xe và cách xác thực và ủy quyền cho người dùng API của bạn một cách an toàn. Trong hướng dẫn này, tôi sẽ hướng dẫn bạn xây dựng một API đơn giản trong PHP từ đầu và tích hợp nó với OKTA để cung cấp xác thực người dùng. Okta là một dịch vụ API cho phép bạn tạo, chỉnh sửa và lưu trữ an toàn tài khoản người dùng và dữ liệu tài khoản người dùng và kết nối chúng với một hoặc nhiều ứng dụng.

Hướng dẫn sẽ không dựa vào bất kỳ thư viện bên ngoài nào để thực hiện tích hợp OKTA hoặc làm việc với các mã thông báo truy cập JWT. Điều kiện tiên quyết duy nhất là PHP, nhà soạn nhạc và tài khoản nhà phát triển OKTA miễn phí.

Tạo bộ xương API còn lại

Bắt đầu bằng cách tạo một dự án trống với thư mục


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
1 và tệp

require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
2 ở cấp cao nhất:

Trong tệp


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
2, xác định một phụ thuộc (thư viện dotenv để bạn có thể giữ chi tiết xác thực OKTA trong tệp

require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
4 mà Lừa bị Git bỏ qua). Ngoài sự phụ thuộc, xác định trình tải tự động PSR-4 để tự động tìm kiếm các lớp PHP trong thư mục

require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
1 của dự án:


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
2

{
    "require": {
        "vlucas/phpdotenv": "^2.4"
    },
    "autoload": {
        "psr-4": {
            "Src\\": "src/"
        }
    }
}

Cài đặt các phụ thuộc:

Điều này sẽ tạo một thư mục


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
7 và cài đặt dotenv bên trong nó.

Tạo tệp


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
8 ở cấp cao nhất để thư mục

require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
7 và tệp

require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
4 cục bộ sẽ bị bỏ qua:

cp .env.example .env
php bootstrap.php
1

Tạo tệp

cp .env.example .env
php bootstrap.php
2 cho các biến xác thực OKTA:

OKTA_CLIENT_ID=
OKTA_CLIENT_SECRET=
OKTA_AUDIENCE=api://default
OKTA_ISSUER=
OKTA_SCOPE=
OKTA_SERVICE_APP_ID=
OKTA_SERVICE_APP_SECRET=

Có hai bộ thông tin đăng nhập - một cho ứng dụng dịch vụ (API REST) ​​và một bộ cho ứng dụng khách sẽ sử dụng API. Một số biến sẽ được chia sẻ giữa hai ứng dụng (nhà phát hành, phạm vi và đối tượng).

Tạo một tệp

cp .env.example .env
php bootstrap.php
3 tải các biến môi trường (sau đó nó cũng sẽ thực hiện một số bootstrapping bổ sung cho dự án của chúng tôi):


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');

Sao chép tệp

cp .env.example .env
php bootstrap.php
2 vào

require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
4 và kiểm tra mã bootstrap để xác nhận nó xuất ra ‘API: // mặc định,:

cp .env.example .env
php bootstrap.php

Thực hiện phiên bản API REST ban đầu

API còn lại sẽ có 3 điểm cuối công khai:

// return all customers
GET /customers

// create a new customer
POST /customers

// charge a customer
POST /customers/{id}/charges

Phiên bản ban đầu sẽ không yêu cầu bất kỳ xác thực/ủy quyền.

Tạo thư mục

cp .env.example .env
php bootstrap.php
6 và tệp
cp .env.example .env
php bootstrap.php
7 để phục vụ như một bộ điều khiển phía trước và xử lý các yêu cầu HTTP đến:


require "../bootstrap.php";

// send some CORS headers so the API can be called from anywhere
header("Access-Control-Allow-Origin: *");
header("Content-Type: application/json; charset=UTF-8");
header("Access-Control-Allow-Methods: OPTIONS,GET,POST,PUT,DELETE");
header("Access-Control-Max-Age: 3600");
header("Access-Control-Allow-Headers: Content-Type, Access-Control-Allow-Headers, Authorization, X-Requested-With");

$uri = parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH);
$requestMethod = $_SERVER["REQUEST_METHOD"];
$uriParts = explode( '/', $uri );

// define all valid endpoints - this will act as a simple router
$routes = [
    'customers' => [
        'method' => 'GET',
        'expression' => '/^\/customers\/?$/',
        'controller_method' => 'index'
    ],
    'customers.create' => [
        'method' => 'POST',
        'expression' => '/^\/customers\/?$/',
        'controller_method' => 'store'
    ],
    'customers.charge' => [
        'method' => 'POST',
        'expression' => '/^\/customers\/(\d+)\/charges\/?$/',
        'controller_method' => 'charge'
    ]
];

$routeFound = null;
foreach ($routes as $route) {
    if ($route['method'] == $requestMethod &&
        preg_match($route['expression'], $uri))
    {
        $routeFound = $route;
        break;
    }
}

if (! $routeFound) {
    header("HTTP/1.1 404 Not Found");
    exit();
}

var_dump($routeFound);

Sửa đổi tệp

cp .env.example .env
php bootstrap.php
3 để nó không xuất ra bất cứ điều gì:


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

Bắt đầu máy chủ PHP tích hợp và kiểm tra bộ điều khiển phía trước:

php -S 127.0.0.1:8000 -t public

Tải

cp .env.example .env
php bootstrap.php
9 và bạn sẽ thấy phản hồi không tìm thấy 404. Tuy nhiên, nếu bạn tải tuyến đường Get hợp lệ:
// return all customers
GET /customers

// create a new customer
POST /customers

// charge a customer
POST /customers/{id}/charges
0, bạn sẽ thấy dữ liệu tuyến được tìm thấy:

array(3) {
  ["method"]=>
  string(3) "GET"
  ["expression"]=>
  string(18) "/^\/customers\/?$/"
  ["controller_method"]=>
  string(5) "index"
}

Bạn sẽ cần một công cụ như Postman để kiểm tra API đầy đủ bao gồm các yêu cầu POST. Lưu ý: Khi thực hiện các yêu cầu POST, hãy đảm bảo đặt loại nội dung thành JSON (

// return all customers
GET /customers

// create a new customer
POST /customers

// charge a customer
POST /customers/{id}/charges
1), loại cơ thể thành RAW và dán tải trọng ở định dạng JSON.

Sử dụng Postman để xác nhận rằng ba tuyến chính xác được hiển thị và tất cả các URL khác dẫn đến phản hồi không tìm thấy 404 trước khi tiến hành thêm.

Tạo một tệp

// return all customers
GET /customers

// create a new customer
POST /customers

// charge a customer
POST /customers/{id}/charges
2 để phục vụ như một bộ điều khiển cho các điểm cuối API. Vì việc triển khai API thực tế không phải là chủ đề của bài viết này, các phương thức điều khiển đã giành được bất cứ điều gì hữu ích - chắc chắn, sẽ không có xác thực dữ liệu hoặc bất kỳ mô hình cơ sở dữ liệu nào để thao tác.


namespace Src\Controllers;

class CustomerController
{
    // list all customers - fake data
    public function index($uri)
    {
        $customers = [
            [
                'name'    => 'Tester',
                'balance' => 120.00
            ],
            [
                'name'    => 'Another Tester',
                'balance' => 100.00
            ]
        ];

        $this->respondOK($customers);
    }

    // create a new customer - fake data
    public function store($uri)
    {
        $customer = [
            'name'    => 'Still A Tester',
            'balance' => 0.00
        ];

        $this->respondCreated($customer);
    }

    // charge a customer - fake data
    public function charge($uri)
    {
        $customerId = $uri[2];

        $data = [
            'customer_id' => (int) $customerId,
            'charge'      => 1.99
        ];

        $this->respondCreated($data);
    }

    private function respondOK($data)
    {
        header('HTTP/1.1 200 OK');
        echo json_encode($data);
    }

    private function respondCreated($data)
    {
        header('HTTP/1.1 201 Created');
        echo json_encode($data);
    }
}

Sửa đổi

cp .env.example .env
php bootstrap.php
7 để ủy quyền cho các phương thức bộ điều khiển để xử lý các tuyến đường cuối:

OKTA_CLIENT_ID=
OKTA_CLIENT_SECRET=
OKTA_AUDIENCE=api://default
OKTA_ISSUER=
OKTA_SCOPE=
OKTA_SERVICE_APP_ID=
OKTA_SERVICE_APP_SECRET=
0

Kiểm tra các điểm cuối tuyến đường trong Postman một lần nữa và xác nhận chúng tạo ra các phản hồi JSON dự kiến.

Sử dụng Okta và OAuth 2.0 để bảo mật API

API sẽ sử dụng OKTA làm máy chủ ủy quyền. Bạn sẽ thực hiện luồng thông tin đăng nhập của khách hàng trong bài tập này. Lưu lượng này được khuyến nghị để xác thực máy tính đến máy khi khách hàng riêng tư và có thể giữ bí mật.

Để đơn giản trong bài viết này, cả ứng dụng máy khách và máy chủ sẽ được lưu trữ trong cùng một kho lưu trữ và sẽ chia sẻ các phần của cấu hình OKTA.

Quá trình ủy quyền hoạt động như thế này:

  • Ứng dụng Máy khách giữ ID máy khách và bí mật.
  • Khách hàng gửi các thông tin này đến OKTA và nhận lại mã thông báo truy cập.
  • Máy khách cung cấp mã thông báo truy cập vào máy chủ API REST với mỗi yêu cầu.
  • Máy chủ xác minh và xác thực mã thông báo OKTA.
  • Nếu mã thông báo hợp lệ, máy chủ cung cấp tài nguyên API.
  • Nếu mã thông báo bị thiếu, không hợp lệ hoặc hết hạn, máy chủ sẽ phản hồi với phản hồi trái phép 401.

Có hai cách để xác minh mã thông báo:

  • Cục bộ bằng cách sử dụng khóa JSON Web (JWK) do Okta cung cấp. Ứng dụng có thể lưu trữ khóa web để tăng tốc quá trình xác thực và thực hiện nó mà không cần bất kỳ yêu cầu HTTP bên ngoài nào.
  • Từ xa bởi okta. Điều này chậm hơn (vì nó yêu cầu yêu cầu HTTP bổ sung) nhưng an toàn hơn, vì nó cung cấp phản hồi thời gian thực nếu mã thông báo vẫn hoạt động hay không.

API sẽ sử dụng phương pháp cục bộ để ủy quyền cho các phương thức

// return all customers
GET /customers

// create a new customer
POST /customers

// charge a customer
POST /customers/{id}/charges
4 và
// return all customers
GET /customers

// create a new customer
POST /customers

// charge a customer
POST /customers/{id}/charges
5, nhưng nó sẽ sử dụng phương pháp từ xa an toàn hơn để ủy quyền cho phương pháp
// return all customers
GET /customers

// create a new customer
POST /customers

// charge a customer
POST /customers/{id}/charges
6 vì phương pháp này yêu cầu mức bảo mật cao nhất, ngay cả với chi phí mất hiệu suất nhỏ.

Khi sử dụng xác minh cục bộ, có thể người dùng có thể bị đình chỉ tại okta nhưng mã thông báo vẫn sẽ được coi là hợp lệ bởi máy chủ API vì nó không kiểm tra trạng thái người dùng trong thời gian thực - nó chỉ xác minh tính hợp lệ của mã thông báo được cung cấp .

Thiết lập okta

Đăng nhập vào tài khoản OKTA của bạn hoặc tạo một tài khoản mới miễn phí, tạo máy chủ ủy quyền của bạn và thiết lập ứng dụng khách của bạn.

Đăng nhập vào bảng điều khiển nhà phát triển của bạn, điều hướng đến API, sau đó vào tab Máy chủ ủy quyền:API, then to the Authorization Servers tab:

Hướng dẫn php oauth2 rest api example - ví dụ về api php oauth2

Nhấp vào liên kết đến máy chủ mặc định của bạn. Sao chép trường

// return all customers
GET /customers

// create a new customer
POST /customers

// charge a customer
POST /customers/{id}/charges
7 từ tab Cài đặt này và thêm nó vào tệp

require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
4 (thay thế URL bằng của riêng bạn):

OKTA_CLIENT_ID=
OKTA_CLIENT_SECRET=
OKTA_AUDIENCE=api://default
OKTA_ISSUER=
OKTA_SCOPE=
OKTA_SERVICE_APP_ID=
OKTA_SERVICE_APP_SECRET=
1

Nhấp vào biểu tượng Chỉnh sửa, chuyển đến tab phạm vi và nhấp vào Thêm phạm vi để thêm phạm vi cho API còn lại:Edit icon, go to the Scopes tab and click Add Scope to add a scope for the REST API:

Hướng dẫn php oauth2 rest api example - ví dụ về api php oauth2

Đặt tên cho nó

// return all customers
GET /customers

// create a new customer
POST /customers

// charge a customer
POST /customers/{id}/charges
9 và để lại phần còn lại của cài đặt như hiện tại.

Thêm phạm vi vào tệp


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
4:

Tạo một ứng dụng khách tiếp theo. Chuyển đến các ứng dụng, nhấp vào Thêm ứng dụng, chọn Dịch vụ, sau đó nhấp vào Tiếp theo:Applications, click Add Application, select Service, then click Next:

Hướng dẫn php oauth2 rest api example - ví dụ về api php oauth2

Tiêu đề Người quản lý khách hàng dịch vụ và nhấp vào xong. Sao chép ID máy khách và bí mật máy khách từ màn hình và cũng đặt chúng vào tệp


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
4:Customer Manager and click Done. Copy the Client ID and Client Secret from the screen, and put them in the

require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
4 file as well:

OKTA_CLIENT_ID=
OKTA_CLIENT_SECRET=
OKTA_AUDIENCE=api://default
OKTA_ISSUER=
OKTA_SCOPE=
OKTA_SERVICE_APP_ID=
OKTA_SERVICE_APP_SECRET=
2

Cuối cùng, hãy tạo một ứng dụng khách (ứng dụng dịch vụ) khác để đại diện cho API, vì API không có quyền truy cập vào thông tin đăng nhập ứng dụng khách hàng, nhưng nó sẽ cần thông tin đăng nhập của khách hàng để tự ủy quyền khi truy cập một số điểm cuối OKTA.

Chuyển đến các ứng dụng, nhấp vào Thêm ứng dụng, chọn Dịch vụ, sau đó nhấp vào Tiếp theo. Tiêu đề API Trình quản lý khách hàng dịch vụ và nhấp xong:Applications, click Add Application, select Service, then click Next. Title the service Customer Manager API and click Done:

Hướng dẫn php oauth2 rest api example - ví dụ về api php oauth2

Sao chép ID máy khách và bí mật máy khách từ màn hình và đặt chúng vào tệp


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
4:Client ID and Client Secret from the screen and put them in the

require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
4 file as well:

OKTA_CLIENT_ID=
OKTA_CLIENT_SECRET=
OKTA_AUDIENCE=api://default
OKTA_ISSUER=
OKTA_SCOPE=
OKTA_SERVICE_APP_ID=
OKTA_SERVICE_APP_SECRET=
3

Có được mã thông báo truy cập từ Okta

Tạo một thư mục


require "../bootstrap.php";

// send some CORS headers so the API can be called from anywhere
header("Access-Control-Allow-Origin: *");
header("Content-Type: application/json; charset=UTF-8");
header("Access-Control-Allow-Methods: OPTIONS,GET,POST,PUT,DELETE");
header("Access-Control-Max-Age: 3600");
header("Access-Control-Allow-Headers: Content-Type, Access-Control-Allow-Headers, Authorization, X-Requested-With");

$uri = parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH);
$requestMethod = $_SERVER["REQUEST_METHOD"];
$uriParts = explode( '/', $uri );

// define all valid endpoints - this will act as a simple router
$routes = [
    'customers' => [
        'method' => 'GET',
        'expression' => '/^\/customers\/?$/',
        'controller_method' => 'index'
    ],
    'customers.create' => [
        'method' => 'POST',
        'expression' => '/^\/customers\/?$/',
        'controller_method' => 'store'
    ],
    'customers.charge' => [
        'method' => 'POST',
        'expression' => '/^\/customers\/(\d+)\/charges\/?$/',
        'controller_method' => 'charge'
    ]
];

$routeFound = null;
foreach ($routes as $route) {
    if ($route['method'] == $requestMethod &&
        preg_match($route['expression'], $uri))
    {
        $routeFound = $route;
        break;
    }
}

if (! $routeFound) {
    header("HTTP/1.1 404 Not Found");
    exit();
}

var_dump($routeFound);
3 mới trong dự án để lưu trữ các tệp ứng dụng máy khách. Tạo tệp

require "../bootstrap.php";

// send some CORS headers so the API can be called from anywhere
header("Access-Control-Allow-Origin: *");
header("Content-Type: application/json; charset=UTF-8");
header("Access-Control-Allow-Methods: OPTIONS,GET,POST,PUT,DELETE");
header("Access-Control-Max-Age: 3600");
header("Access-Control-Allow-Headers: Content-Type, Access-Control-Allow-Headers, Authorization, X-Requested-With");

$uri = parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH);
$requestMethod = $_SERVER["REQUEST_METHOD"];
$uriParts = explode( '/', $uri );

// define all valid endpoints - this will act as a simple router
$routes = [
    'customers' => [
        'method' => 'GET',
        'expression' => '/^\/customers\/?$/',
        'controller_method' => 'index'
    ],
    'customers.create' => [
        'method' => 'POST',
        'expression' => '/^\/customers\/?$/',
        'controller_method' => 'store'
    ],
    'customers.charge' => [
        'method' => 'POST',
        'expression' => '/^\/customers\/(\d+)\/charges\/?$/',
        'controller_method' => 'charge'
    ]
];

$routeFound = null;
foreach ($routes as $route) {
    if ($route['method'] == $requestMethod &&
        preg_match($route['expression'], $uri))
    {
        $routeFound = $route;
        break;
    }
}

if (! $routeFound) {
    header("HTTP/1.1 404 Not Found");
    exit();
}

var_dump($routeFound);
4:

OKTA_CLIENT_ID=
OKTA_CLIENT_SECRET=
OKTA_AUDIENCE=api://default
OKTA_ISSUER=
OKTA_SCOPE=
OKTA_SERVICE_APP_ID=
OKTA_SERVICE_APP_SECRET=
4

Gọi tệp từ dòng lệnh và sao chép mã thông báo:

Mã thông báo sẽ trông giống như thế này:

OKTA_CLIENT_ID=
OKTA_CLIENT_SECRET=
OKTA_AUDIENCE=api://default
OKTA_ISSUER=
OKTA_SCOPE=
OKTA_SERVICE_APP_ID=
OKTA_SERVICE_APP_SECRET=
5

Cập nhật bộ điều khiển phía trước để nó yêu cầu ủy quyền cho tất cả các điểm cuối API (sử dụng xác thực cục bộ cho các phương thức chỉ mục và lưu trữ và xác thực từ xa cho phương thức tính phí). Tại đây, mã đầy đủ của

cp .env.example .env
php bootstrap.php
7 cho rõ ràng:

OKTA_CLIENT_ID=
OKTA_CLIENT_SECRET=
OKTA_AUDIENCE=api://default
OKTA_ISSUER=
OKTA_SCOPE=
OKTA_SERVICE_APP_ID=
OKTA_SERVICE_APP_SECRET=
6

Có rất nhiều điều đang diễn ra ở đây nhưng những phần quan trọng nhất là:

  • Phương pháp
    
    require "../bootstrap.php";
    
    // send some CORS headers so the API can be called from anywhere
    header("Access-Control-Allow-Origin: *");
    header("Content-Type: application/json; charset=UTF-8");
    header("Access-Control-Allow-Methods: OPTIONS,GET,POST,PUT,DELETE");
    header("Access-Control-Max-Age: 3600");
    header("Access-Control-Allow-Headers: Content-Type, Access-Control-Allow-Headers, Authorization, X-Requested-With");
    
    $uri = parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH);
    $requestMethod = $_SERVER["REQUEST_METHOD"];
    $uriParts = explode( '/', $uri );
    
    // define all valid endpoints - this will act as a simple router
    $routes = [
        'customers' => [
            'method' => 'GET',
            'expression' => '/^\/customers\/?$/',
            'controller_method' => 'index'
        ],
        'customers.create' => [
            'method' => 'POST',
            'expression' => '/^\/customers\/?$/',
            'controller_method' => 'store'
        ],
        'customers.charge' => [
            'method' => 'POST',
            'expression' => '/^\/customers\/(\d+)\/charges\/?$/',
            'controller_method' => 'charge'
        ]
    ];
    
    $routeFound = null;
    foreach ($routes as $route) {
        if ($route['method'] == $requestMethod &&
            preg_match($route['expression'], $uri))
        {
            $routeFound = $route;
            break;
        }
    }
    
    if (! $routeFound) {
        header("HTTP/1.1 404 Not Found");
        exit();
    }
    
    var_dump($routeFound);
    
    6 cung cấp xác minh từ xa mã thông báo bằng cách sử dụng cuộc gọi đến điểm cuối hướng nội của Okta. Nó có thể cho biết rằng mã thông báo là hợp lệ hoặc không hợp lệ/hết hạn và nó cũng có thể xác nhận rằng người dùng OKTA vẫn đang hoạt động.
  • Phương pháp
    
    require "../bootstrap.php";
    
    // send some CORS headers so the API can be called from anywhere
    header("Access-Control-Allow-Origin: *");
    header("Content-Type: application/json; charset=UTF-8");
    header("Access-Control-Allow-Methods: OPTIONS,GET,POST,PUT,DELETE");
    header("Access-Control-Max-Age: 3600");
    header("Access-Control-Allow-Headers: Content-Type, Access-Control-Allow-Headers, Authorization, X-Requested-With");
    
    $uri = parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH);
    $requestMethod = $_SERVER["REQUEST_METHOD"];
    $uriParts = explode( '/', $uri );
    
    // define all valid endpoints - this will act as a simple router
    $routes = [
        'customers' => [
            'method' => 'GET',
            'expression' => '/^\/customers\/?$/',
            'controller_method' => 'index'
        ],
        'customers.create' => [
            'method' => 'POST',
            'expression' => '/^\/customers\/?$/',
            'controller_method' => 'store'
        ],
        'customers.charge' => [
            'method' => 'POST',
            'expression' => '/^\/customers\/(\d+)\/charges\/?$/',
            'controller_method' => 'charge'
        ]
    ];
    
    $routeFound = null;
    foreach ($routes as $route) {
        if ($route['method'] == $requestMethod &&
            preg_match($route['expression'], $uri))
        {
            $routeFound = $route;
            break;
        }
    }
    
    if (! $routeFound) {
        header("HTTP/1.1 404 Not Found");
        exit();
    }
    
    var_dump($routeFound);
    
    7 cung cấp xác thực cục bộ của mã thông báo. Bạn có thể nhận thấy rằng trong ví dụ này, nó cũng bắt đầu bằng một cuộc gọi đến Okta để lấy các khóa web JSON để xác minh, do đó, nó không phải lúc nào cũng nhanh hơn xác thực từ xa. Tuy nhiên, trong một ứng dụng thực sự, các khóa này sẽ được lưu trữ tại địa phương trong nhiều tháng và cuộc gọi đến Okta để làm mới chúng sẽ xảy ra khá hiếm khi.

Xác thực cục bộ xác minh các thuộc tính sau của mã thông báo:

  • Xác minh chữ ký
  • Thời gian hết hạn (phải có trong tương lai)
  • Nhà phát hành, đối tượng, ID máy khách (phải khớp với cấu hình OKTA cục bộ)
  • ID chính
  • Thuật toán ký kết

Ở bước tiếp theo, bạn sẽ kiểm tra xác thực bằng Postman.

Cung cấp mã thông báo truy cập dưới dạng tiêu đề


require "../bootstrap.php";

// send some CORS headers so the API can be called from anywhere
header("Access-Control-Allow-Origin: *");
header("Content-Type: application/json; charset=UTF-8");
header("Access-Control-Allow-Methods: OPTIONS,GET,POST,PUT,DELETE");
header("Access-Control-Max-Age: 3600");
header("Access-Control-Allow-Headers: Content-Type, Access-Control-Allow-Headers, Authorization, X-Requested-With");

$uri = parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH);
$requestMethod = $_SERVER["REQUEST_METHOD"];
$uriParts = explode( '/', $uri );

// define all valid endpoints - this will act as a simple router
$routes = [
    'customers' => [
        'method' => 'GET',
        'expression' => '/^\/customers\/?$/',
        'controller_method' => 'index'
    ],
    'customers.create' => [
        'method' => 'POST',
        'expression' => '/^\/customers\/?$/',
        'controller_method' => 'store'
    ],
    'customers.charge' => [
        'method' => 'POST',
        'expression' => '/^\/customers\/(\d+)\/charges\/?$/',
        'controller_method' => 'charge'
    ]
];

$routeFound = null;
foreach ($routes as $route) {
    if ($route['method'] == $requestMethod &&
        preg_match($route['expression'], $uri))
    {
        $routeFound = $route;
        break;
    }
}

if (! $routeFound) {
    header("HTTP/1.1 404 Not Found");
    exit();
}

var_dump($routeFound);
8 với giá trị

require "../bootstrap.php";

// send some CORS headers so the API can be called from anywhere
header("Access-Control-Allow-Origin: *");
header("Content-Type: application/json; charset=UTF-8");
header("Access-Control-Allow-Methods: OPTIONS,GET,POST,PUT,DELETE");
header("Access-Control-Max-Age: 3600");
header("Access-Control-Allow-Headers: Content-Type, Access-Control-Allow-Headers, Authorization, X-Requested-With");

$uri = parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH);
$requestMethod = $_SERVER["REQUEST_METHOD"];
$uriParts = explode( '/', $uri );

// define all valid endpoints - this will act as a simple router
$routes = [
    'customers' => [
        'method' => 'GET',
        'expression' => '/^\/customers\/?$/',
        'controller_method' => 'index'
    ],
    'customers.create' => [
        'method' => 'POST',
        'expression' => '/^\/customers\/?$/',
        'controller_method' => 'store'
    ],
    'customers.charge' => [
        'method' => 'POST',
        'expression' => '/^\/customers\/(\d+)\/charges\/?$/',
        'controller_method' => 'charge'
    ]
];

$routeFound = null;
foreach ($routes as $route) {
    if ($route['method'] == $requestMethod &&
        preg_match($route['expression'], $uri))
    {
        $routeFound = $route;
        break;
    }
}

if (! $routeFound) {
    header("HTTP/1.1 404 Not Found");
    exit();
}

var_dump($routeFound);
9 với mỗi yêu cầu HTTP cho API bạn thực hiện. Giá trị ví dụ của tiêu đề:

OKTA_CLIENT_ID=
OKTA_CLIENT_SECRET=
OKTA_AUDIENCE=api://default
OKTA_ISSUER=
OKTA_SCOPE=
OKTA_SERVICE_APP_ID=
OKTA_SERVICE_APP_SECRET=
7

Kiểm tra các điểm cuối một lần nữa trong Postman. Nếu bạn không cung cấp mã thông báo hợp lệ, bạn sẽ nhận được phản hồi


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();
0. Nếu bạn cung cấp mã thông báo hợp lệ, bạn nên nhận các phản hồi JSON bình thường.

Thu hồi mã thông báo truy cập

Tạo một tệp mới


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();
1:

OKTA_CLIENT_ID=
OKTA_CLIENT_SECRET=
OKTA_AUDIENCE=api://default
OKTA_ISSUER=
OKTA_SCOPE=
OKTA_SERVICE_APP_ID=
OKTA_SERVICE_APP_SECRET=
8

Gọi công cụ như thế này (thay thế


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();
2 bằng mã thông báo bạn muốn thu hồi):

OKTA_CLIENT_ID=
OKTA_CLIENT_SECRET=
OKTA_AUDIENCE=api://default
OKTA_ISSUER=
OKTA_SCOPE=
OKTA_SERVICE_APP_ID=
OKTA_SERVICE_APP_SECRET=
9

Example:


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();

// test that the variables are loaded:
echo getenv('OKTA_AUDIENCE');
0

Sau khi thu hồi mã thông báo, hãy thử lại tất cả các cuộc gọi API với mã thông báo đó. Bạn sẽ thấy rằng


require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();
3 và

require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();
4 vẫn hoạt động (vì chúng chỉ thực hiện xác thực cục bộ), nhưng

require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();
5 trả về phản hồi

require 'vendor/autoload.php';
use Dotenv\Dotenv;

$dotenv = new DotEnv(__DIR__);
$dotenv->load();
0 (vì xác thực từ xa không thành công vì mã thông báo không còn hoạt động nữa).

Tìm hiểu thêm về ủy quyền OAuth 2.0 trong PHP

Bạn có thể tìm thấy toàn bộ ví dụ mã trên GitHub.

Nếu bạn muốn đào sâu hơn vào các chủ đề được đề cập trong bài viết này, các tài nguyên sau đây là một điểm khởi đầu tuyệt vời:

  • Phản cấp PHP với OAuth 2.0 và OKTA
  • Tạo và xác minh JWTS trong PHP với OAuth 2.0
  • Xác thực mã thông báo trong PHP

Giống như những gì bạn đã học được hôm nay? Theo dõi chúng tôi trên Twitter, như chúng tôi trên Facebook, hãy xem chúng tôi trên LinkedIn và đăng ký kênh YouTube của chúng tôi để biết nội dung tuyệt vời hơn!

Làm thế nào sử dụng OAuth 2.0 cho các cuộc gọi API REST trong PHP?

Điều kiện tiên quyết duy nhất là PHP, nhà soạn nhạc và tài khoản nhà phát triển OKTA miễn phí ...
Tạo bộ xương API còn lại ..
Thực hiện phiên bản API REST ban đầu ..
Sử dụng Okta và OAuth 2.0 để bảo mật API ..
Thiết lập okta ..
Có được mã thông báo truy cập từ Okta ..
Thêm ủy quyền mã thông báo vào API ..
Thu hồi mã thông báo truy cập ..

OAuth2 2.0 hoạt động như thế nào trong API REST?

OAuth2 cho phép ủy quyền mà không cần ứng dụng bên ngoài nhận địa chỉ email hoặc mật khẩu của người dùng.Thay vào đó, ứng dụng bên ngoài nhận được một mã thông báo cho phép truy cập vào tài khoản của người dùng.Người dùng có thể thu hồi mã thông báo cho một ứng dụng mà không ảnh hưởng đến quyền truy cập bởi bất kỳ ứng dụng nào khác.allows authorization without the external application getting the user's email address or password. Instead, the external application gets a token that authorizes access to the user's account. The user can revoke the token for one application without affecting access by any other application.

OAuth2 trong PHP là gì?

League/OAuth2-Server là một triển khai tuân thủ tiêu chuẩn của máy chủ ủy quyền OAuth 2.0 được viết bằng PHP giúp làm việc với tầm thường của OAuth 2.0.Bạn có thể dễ dàng định cấu hình máy chủ OAuth 2.0 để bảo vệ API của mình bằng mã thông báo truy cập hoặc cho phép khách hàng yêu cầu mã thông báo truy cập mới và làm mới chúng.a standards compliant implementation of an OAuth 2.0 authorization server written in PHP which makes working with OAuth 2.0 trivial. You can easily configure an OAuth 2.0 server to protect your API with access tokens, or allow clients to request new access tokens and refresh them.

Làm cách nào để thêm OAuth vào API REST?

Tạo API nhà cung cấp OAuth 2.0..
Trong một cửa sổ lệnh, thay đổi sang thư mục dự án mà bạn đã tạo trong hướng dẫn hướng dẫn: Tạo định nghĩa API gọi RESKE ..
Trong trình thiết kế API, nhấp vào tab API ..
Nhấp vào Thêm> API nhà cung cấp OAuth 2.0 ..
Hoàn thành các trường theo bảng sau: ....
Nhấp vào Tạo API ..