Elm http请求返回NetworkError以获取成功请求

Mic*_*Fox 10 http elm

我有很多使用React构建Web应用程序但是想学习Elm的经验.我几天来一直在讨论HTTP请求问题.

我在localhost:8080运行Elm应用程序,在localhost运行我的支持API:8081.每当我发出HTTP请求(我已尝试过GET和POST请求)时,我都会遇到NetworkError.我一直在研究Elm JSON解码器,并认为这可能是我的问题存在但我已经尝试从我的服务器发送简单的字符串并在我的Elm应用程序中使用Decode.string解码器,我仍然得到NetworkError.

这是我的代码目前的样子:

Commands.elm

module Commands exposing (..)

import Models exposing (..)
import Msg exposing (..)
import Http
import Json.Decode as Decode
import Json.Encode as Encode


createTempUser : Model -> Cmd Msg
createTempUser model =
  let
    tempUserBody =
      [ ( "firstname", Encode.string model.firstname )
      , ( "lastname", Encode.string model.lastname )
      , ( "phone", Encode.string model.phone )
      ]
        |> Encode.object
        |> Http.jsonBody

    url =
      myAPIUrl ++ "/endpoint"

    contentType = Http.header "Content-type" "text/plain"

    post =
      Http.request
        { method = "POST"
        , headers =  [contentType]
        , url = url
        , body = tempUserBody
        , expect = Http.expectJson decodeApiResponse
        , timeout = Nothing
        , withCredentials = False
        }

  in
    Http.send Msg.TempUserCreated post


decodeApiResponse : Decode.Decoder ApiResponse
decodeApiResponse =
  Decode.map4 ApiResponse
    (Decode.at ["status"] Decode.int)
    (Decode.at ["message"] Decode.string)
    (Decode.at ["created"] Decode.int)
    (Decode.at ["error"] Decode.string)


myAPIUrl : String
myAPIUrl = "http://localhost:8081"
Run Code Online (Sandbox Code Playgroud)

Models.elm

module Models exposing (..)


type alias ApiResponse =
  { status: Int
  , message: String
  , created: Int
  , error: String
  }
Run Code Online (Sandbox Code Playgroud)

Msg.elm

module Msg exposing (..)

import Navigation exposing (Location)
import Models exposing (..)
import Http


type Msg
  = ChangeLocation String
  | OnLocationChange Location
  | CreateTemporaryUser
  | TempUserCreated ( Result Http.Error ApiResponse )
Run Code Online (Sandbox Code Playgroud)

Update.elm

module Update exposing (..)

import Msg exposing (Msg)
import Models exposing (..)
import Routing exposing (..)
import Commands exposing (..)
import Navigation

update : Msg -> Model -> (Model, Cmd Msg)
update msg model =
  case msg of
    Msg.ChangeLocation path ->
      ( { model | changes = model.changes + 1 }, Navigation.newUrl path )

    Msg.OnLocationChange location ->
      ( { model | error = "", route = parseLocation(location) }, Cmd.none )

    Msg.CreateTemporaryUser ->
      ( model, createTempUser model )

    Msg.TempUserCreated (Ok res) ->
       update (Msg.ChangeLocation signupCodePath) { model | httpResponse = toString(res) }

    Msg.TempUserCreated (Err err) ->
      ( { model | error = toString(err) }, Cmd.none )
Run Code Online (Sandbox Code Playgroud)

Chrome的网络开发工具显示响应

{"status":200,"message":"Successfully inserted temporary 
user","created":1518739596447,"error":""}
Run Code Online (Sandbox Code Playgroud)

我认为这可能是所有相关的代码,但如果还有更多需要看到我将进行更新,包括所请求的代码.我承认我没有完全理解Elm Json.Decode库,但我的印象是,如果这是问题所在,我会得到一个包含额外上下文的UnexpectedPayload错误.

Mic*_*Fox 8

@Sidney和@SimonH,

谢谢你为我调查这个,我感觉很糟糕,因为这毕竟不是榆树问题.

解决方案最终使用服务器上的CORS中间件添加"Access-Control-Allow-Origin"标头.服务器仍然以200状态响应,甚至包括整个成功的响应机构,但这导致了Elm的Http结果失败.

再次感谢您的时间和思想!

  • 这有点像 Elm 问题,因为错误的原因(即缺少 CORS 标头)在 Elm 代码内发出请求与 Elm 代码接收到 NetworkError 之间的某处被吞没或丢失。 (2认同)