Подписки Netflix DGS

Я слежу за документацией по подпискам DGS, и я не получаю никаких ошибок, но и не получаю никаких данных.

Настройка очень проста. В файле schema.graphqls я определил подписку:

      type Subscription {
    ratings: Rating
}

type Rating {
    stars: Int
}

А код Java выглядит следующим образом:

      @DgsComponent
public class SubscriptionDataFetcher {
    @DgsData(parentType = "Subscription", field = "ratings")
    public Publisher<Rating> ratings() {
        return Flux.interval(Duration.ofSeconds(1)).map(t -> new Rating(4));
    }
}

Если я теперь подключаю веб-сокет к своему бэкэнду, он подключается нормально, но не получает никаких данных, как ожидалось (неважно, как я это делаю, также пытался использовать JavaScript, также подключается отлично, но не получает никаких данных).

Например, используя curl для подключения (но при использовании JavaScript результат тот же, подключается, но нет данных):

      curl -o - --http1.1 \
    --include \
    --no-buffer \
    --header "Connection: Upgrade" \
    --header "Upgrade: websocket" \
    --header "Host: localhost:8443" \
    --header "Origin: https://localhost:8443" \
    --header "Sec-WebSocket-Key: SGVsbG8sIHdvcmxkIQ==" \
    --header "Sec-WebSocket-Version: 13" \
    https://localhost:8443/subscriptions\?query\=ewoicXVlcnkiOiAic3Vic2NyaXB0aW9uIHsgIHN0b2NrcyB7bmFtZX0gfSIKfQ==

Я также пробовал подключиться через интерфейс Graphiql, но это дает ошибку:

      subscription {
  ratings {
    stars
  }
}

Сообщение об ошибке:

      {
  "message": "response is not defined",
  "stack": "ReferenceError: response is not defined\n    at https://localhost:8443/graphiql:46:35\n    at async Object.onRun (https://unpkg.com/graphiql/graphiql.min.js:1:540500)"
}

Еще одна вещь, которая мне непонятна из примеров по ссылке, - это как на самом деле управлять подписками. Так, например, скажем, я хочу опубликовать уведомление, если происходит мутация. Любые указания на то, как это можно сделать с помощью инфраструктуры Netflix DGS, также будут очень благодарны.

1 ответ

Решение

К сожалению, интерфейс graphiql, поставляемый с DGS, похоже, не обрабатывает подписки должным образом - если вы добавите playground-spring-boot-starter к вашему проекту, более совершенный инструмент будет доступен по адресу /playground, который полностью поддерживает подписки. Если вы попробуете свою подписку там, она должна работать (при условии, что вы уже добавилиgraphql-dgs-subscriptions-websockets-autoconfigure согласно документации).

Что касается вашего второго вопроса о том, как опубликовать уведомление, если происходит мутация - это, к сожалению, отсутствует в документации, но есть пример в репозитории примеров .

Я немного урезал пример здесь. Если вы хотите поддержать подписку и мутацию следующим образом:

      @DgsSubscription
public Publisher<Review> reviewAdded() {
    return reviewsService.getReviewsPublisher();
}

@DgsMutation
public Review addReview(@InputArgument SubmittedReview review) {
    return reviewsService.saveReview(review);
}

Внутри вашего сервиса вы должны создать Flux (для возврата подписчикам) и сохранить ссылку на его эмиттер, чтобы вы могли вызывать его при каждом изменении.

      @Service
public class ReviewsService {

    private FluxSink<Review> reviewsStream;
    private ConnectableFlux<Review> reviewsPublisher;

    @PostConstruct
    public void init() {
        Flux<Review> publisher = Flux.create(emitter -> {
            reviewsStream = emitter;
        });

        reviewsPublisher = publisher.publish();
        reviewsPublisher.connect();
    }

    public Review saveReview(SubmittedReview reviewInput) {
        Review review = Review.newBuilder()
                .username(reviewInput.getUsername())
                .starScore(reviewInput.getStarScore())
                .submittedDate(OffsetDateTime.now()).build();

        // Save to the database, etc.

        reviewsStream.next(review); // publishes the review to subscribers
        return review;
    }

    public Publisher<Review> getReviewsPublisher() {
        return reviewsPublisher;
    }
}
Другие вопросы по тегам