Quick Start Guide

FRA has selected Open Data (OData) as the API protocol to be used to retrieve FRA data. OData uses the Representational state transfer (REST) model for all data requests. Although the OData protocol supports a full suite of Create, Update, and Delete (CRUD) functionality, FRA supports only commands associated with retrieving data.

The following sites provide numerous examples and additional information for the use of OData:

API Authorization

All data requests, including the examples on this page, must include a securely approved GCIS user account and an FRA-supplied API access token that has been assigned for each authorized session. To get an GCIS user account, you will need to register at the secure Grade Crossing Inventory System (GCIS). Authenticated users will be provided authorization to GET and POST GCIS data.
The Authorization can be included in the HTTPS request using Base64Encoded string:
  • Using the Authorization request header:
    GET https://safetydata.fra.dot.gov/MasterWebService/SecureApi/api/Authenticate HTTP/1.1
    Host: safetydata.fra.dot.gov
    Authorization: Basic Base64Encoding(username:password) 
                    
  • How to include the Authorization Header:
    C# Client
    var username = "myUsername";
    var password = "myPassword";
    			
    var bytes = Encoding.ASCII.GetBytes(username  + ":" + password);
    var basicAuthentication = Convert.ToBase64String(bytes);
    
    var httpClient = new HttpClient();
    httpClient.DefaultRequestHeaders.Clear();
    httpClient.DefaultRequestHeaders.Add("Authorization", $"Basic {basicAuthentication}");
    var response = httpClient.GetStringAsync("https://safetydata.fra.dot.gov/MasterWebService/SecureApi/api/Authenticate");
    
    Java Client
    String username = "myUsername";
    String password = "myPassword";
    
    UsernamePasswordCredentials creds = new UsernamePasswordCredentials(username, password);
    BasicCredentialsProvider provider = new BasicCredentialsProvider();
    provider.setCredentials(AuthScope.ANY, creds);
    
    HttpClient client = HttpClientBuilder.create().setDefaultCredentialsProvider(provider).build();
    HttpGet request = new HttpGet("https://safetydata.fra.dot.gov/MasterWebService/SecureApi/api/Authenticate");
    
    HttpResponse response = client.execute(request);
    
    Python Client
    from http.client import HTTPSConnection
    from base64 import b64encode
    
    def basic_auth(username, password):
    	token = b64encode(f"{username}:{password}".encode('utf-8')).decode("ascii")
    	return f'Basic {token}'
    
    username = "myUsername"
    password = "myPassword"
    
    c = HTTPSConnection("https://safetydata.fra.dot.gov/MasterWebService/SecureApi/api/Authenticate")
    
    headers = { 'Authorization' : basic_auth(username, password) }
    c.request('GET', '/', headers=headers)
    
    res = c.getresponse()
    
    data = res.read()  
    				
  • If successful, an Access Token object will be returned:
    Token:af63163c-a581-49da-a8e4-21321e099c02
    UserName:user@user.com
    IssueTime:2014-04-22T14:06:48.4545975-04:00
    ExpireTime:2014-04-22T14:36:48.4545975-04:00
    HasExpired:false
                    
    All subsequent calls to the API must contain the API Access Token as part of the request, otherwise, a Request did not include an authorized access token will be returned.
  • If unsuccessful, an error message will be returned.

API Access Tokens

Once successfully logged in using your securely approved GCIS user account, you will be assigned an API Access Token for the current session. To get an access token you will need to Sign In using your securely approved GCIS user account. A logged-in user can then view their access tokens on the Data Sampler page.

The API access token can be included in the HTTP request in either of two ways:

  • Using the X-ApiAccessToken request header:
    GET https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings HTTP/1.1
    Host: safetydata.fra.dot.gov
    X-ApiAccessToken: <token-value>
                        
  • Using the token URI query string parameter:
    https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings?token=<token-value>

Note:
Tokens remain valid for 20 minutes from the moment they are generated.
A new token will not be generated until the existing token has expired.

Response Formats

Users also have the option to receive response data in JSON or XML-based Atom format. Although the default for the FRA is XML, the user can specify the desired format in the request via either the $format query string parameter or the standard Accept HTTP header.

The format can be specified as one of the well-known MIME content type such as application/json for JSON or text/xml for XML. As a short form, you may alternately use json, xml, or atom.

  • Specifying response format via the query string:
    https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings?$format=xml
    https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings?$format=json
    https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings?$format=atom
    https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings?$format=application/json
    https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings?$format=application/atom+xml
                        
  • Specifying response format via the HTTP request headers:
    GET https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings HTTP/1.1
    Host: safetydata.fra.dot.gov
    Accept: application/atom+xml
                        
    GET https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings HTTP/1.1
    Host: safetydata.fra.dot.gov
    Accept: application/json
                        

Paging

Paging is an integral part of the querying logic, as such only limited number of results can be requested at a time. To page, use the $top and $skip parameters.

Get all Published crossing data 1000 pages at a time
page 1
https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings?$top=1000&$filter=ReportStatus eq 'Published'&token=<token-value>
page 2
https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings?$top=1000&$skip=1000&$filter=ReportStatus eq 'Published'&token=<token-value>
....
page 5
https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings?$top=1000&$skip=4000&$filter=ReportStatus eq 'Published'&token=<token-value>

Sample Data GET Requests

Note:
When you submit a Get request with filters, please make sure there are no single quotes (‘) for the fields that are marked as decimal or double.
To get value types for all fields please request the metadata document using the URL from the 'Requesting MetaData' section on this page.

To access data, insert your assigned token into the request for query results to be returned. If you do not have a token you will need to Sign In to retrieve your assigned token.

The following are sample requests to retrieve Crossing data using OData query expressions:

Get latest crossing data for a specific crossing
Response is a list of data last submitted for a specific crossing location <token-value>
Get current and all historical crossing data for a specific crossing
Response is a list of all data marked as historical for a specific crossing location along with the active record <token-value>
Get historical crossing data for a specific crossing
Response is a list of all data marked as historical for a specific crossing location <token-value>
Get all Published crossing data
Response is a list of all crossings and their supporting data <token-value>
Get all pending crossing data for your agency
Response is a list of data last submitted for a specific crossing location <token-value>
Get all Published & Expired crossing data by CrossingID
Response is a list of all crossings and their supporting data <token-value>
Get all crossing data with errors for your agency
Response is a list of crossings that has not passed validation after a submission was done <token-value>
Get crossing submission validation errors
Response is a list of crossings that has not passed validation after a submission was done <token-value>
Get all crossing data with Submission Id
Response is a list of data last submitted for a specific crossing location <token-value>
Get crossing data by Railroad
Response is a list of all crossings belonging to a specific Railroad <token-value>
Get crossing data by State
Response is a list of all crossings belonging to a specific State <token-value>
Get all public crossing data
Response is a list of all public crossings and their supporting data <token-value>
Get all private crossing data
Response is a list of all private crossings and their supporting data <token-value>
Get all lookups
Response is a list of lookup values. The lookup ID’s are used to make updates to crossing values <token-value>
Get all Locations
Response is a list of lookup values. The values are used to make updates to the location part crossing values <token-value>

Sample Data Submissions using POST, PATCH or PUT Requests

Note:
When you submit a Post, PATCH or PUT requests, please use a single quoutes for the fields that are marked as decimal.
To get value types for all fields please request the metadata document using the URL from the 'Requesting MetaData' section on this page.
Result
When submitting a crossing data that is not formatted properly, a 200 or 400 result type can be expected. Receiving a 400 bad request may be due to sending an invalid request.
e.g. Empty body or failure due to validation errors
    HTTP/1.1 200 OK
    {"SubmissionID":"6bfecdec-6a78-4c19-a760-4cb2002d9cfa","Message":"Success","HasError":false,"Processed":true, "Comments":""}
    HTTP/1.1 400 Bad Request
    {"SubmissionID":"6bfecdec-6a78-4c19-a760-4cb2002d9cfa","Message":"The submission was processed with validation errors","HasError":true,"Processed":true, "Comments":"Pending record has been created"}
Send single Crossing Data for Processing
A single crossing can be sent using POST, PATCH or PUT endpoints.
Note:
These submissions will not require the generation of a new token per each HTTP request if they all fall within the same 20 minute span.
The following POST request will mark the crossing as closed.
POST https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings?token=<token-value>
Content-type: application/json
{
	"Crossings":
    [
        {
           "CrossingId": "857733N",
           "ReasonId":16,
           "ReportType":"Full Inventory Record ",
           "Railroad":"CSX"   
        }
    ]
}
The following PATCH will update the street, sets the multi-select value for Type of Train and sets HSR Corridor ID to be N/A
PATCH https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings('350152L')?token=<token-value>
Content-type: application/json
{
	"Crossings":
    [
        {
           "CrossingId": "857733N",
           "ReasonId":14,
           "ReportType":"Full Inventory Record ",
           "Railroad":"CSX",
           "TypeTrnSrvcIDs":"11,16,14",
           "Street":"Main",
           "BlockNumb":"12",
           "HscoRrid":"NA"
        }
    ]
}
The following PUT will update field I.7 Do Other Railroads Operate a Separate Track at Crossing? to Yes and UP as one of the Railroad operator, set field I.8 Do Other Railroads Operate Over Your Track at Crossing? to No, and update field I.34 Railroad Contact with the telephone number. It also updates field III.2.D Advance Warning Signs, W10-1, W10-4, and W10-12 with a numeric value or null.
PUT https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings('350152L')?token=<token-value>
Content-type: application/json
{
	"Crossings":
    [
         {
           "CrossingId": "857733N",
           "ReasonId":14,
           "ReportType":"Full Inventory Record ",
           "Railroad":"CSX"   ,
           "SepInd":"1",
           "SepRr1":"UP",
           "SameInd":"2",
           "RrDiv":"NA",
           "DevelTypID":"11",
           "SpselIDs":"11,12",
           "LLsource":"1",
           "Lt1PassMov":"1",
           "RrCont":"8002320144",
           "AdvWarn":"1,2,12",
           "AdvW10_1":"5",
           "AdvW10_2":"3",
           "AdvW10_3":null,
           "AdvW10_4":null,
           "AdvW10_11":null,
           "AdvW10_12":"1"
        } 
    ]
} 
Send multiple Crossing Data for Processing
Multiple crossing can be sent using the POST endpoint. Multiple crossing submissions can process up to 10 crossings at a time.
Note:
Error messages are generated for each submission. This may not provide as much specific information as desired if many crossings are submitted together.
To receive crossing level error reports you should use single Crossing Data requests.
The following POST combines all three requests mentioned in the sections above.
POST https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings?token=<token-value>
{
   "Crossings":
    [
      {
        "CrossingId": "852324E",
        "ReasonId": 14,
        "ReportType": "Full Inventory Record",
        "Railroad": "WVRD",
        "StateCD": "41",
        "CntyCD": "41053",
        "CityCD": "410531070",
        "DayThru":  '1',
        "NghtThru": '2',
        "TotalSwt": "3",
        "TotalLtr": "0",
        "RrNarr1": "(X)",
        "ReportingAgencyTypeID":'1'
      },
      {
         "CrossingId":"476229X",
         "ReasonId":14,
         "ReportType":"Full Inventory Record ",
         "Railroad":"EIRC",
         "TypeTrnSrvcIDs":"11,16,14",
         "Street":"Main",
         "BlockNumb":"12",
         "HscoRrid":"NA"
      },
      {
         "CrossingId":"852324E",
         "ReasonId":14,
         "ReportType":"Full Inventory Record ",
         "Railroad":"EIRC",
         "SepInd":"1",
         "SepRr1":"UP",
         "SameInd":"2",
         "RrDiv":"NA",
         "DevelTypID":"11",
         "SpselIDs":"11,12",
         "LLsource":"1",
         "Lt1PassMov":"1",
         "RrCont":"8002320144",
         "AdvWarn":"1,2,12",
         "AdvW10_1":"5",
         "AdvW10_2":"3",
         "AdvW10_3":null,
         "AdvW10_4":null,
         "AdvW10_11":null,
         "AdvW10_12":"1"
      }
   ],
   "isCancelRequest":false
}
  
Send Crossing using XML
Sending the data in XML format is exactly the same as above, except the data has to be formatted as XML and the Content-Type has to be set to application/xml.
                     
POST https://safetydata.fra.dot.gov/MasterWebService/SecureApi/gcis/v1/odata/Crossings?token=<token-value>
    Content-type: application/xml
<CrossingProcessRequest>
    <Crossings>
        <Crossing>
        <CrossingId>669335R</CrossingId>
        <PosXing>1</PosXing>        
        <Railroad>BNSF</Railroad>
        <ReasonId>14</ReasonId>
  	<PrempType null="true" />
        <PrfxMilePost>NON</PrfxMilePost>
        <PrvxSign>2</PrvxSign>
        </Crossing>
        <Crossing>
	<CrossingId>393835W</CrossingId>
        <DayThru>0.0</DayThru>
        <Latitude>45.4495350</Latitude>
        <Longitude>-99.3409190</Longitude>
        </Crossing>
    </Crossings>
    <isCancelRequest>false</isCancelRequest>
</CrossingProcessRequest>