{"id":15662955,"url":"https://github.com/mattsse/crossref-rs","last_synced_at":"2025-07-04T21:05:05.795Z","repository":{"id":47737323,"uuid":"172197014","full_name":"mattsse/crossref-rs","owner":"mattsse","description":"A rust client for the Crossref-API","archived":false,"fork":false,"pushed_at":"2024-03-22T11:22:12.000Z","size":119,"stargazers_count":19,"open_issues_count":3,"forks_count":6,"subscribers_count":2,"default_branch":"master","last_synced_at":"2025-06-01T18:59:17.004Z","etag":null,"topics":["api","crossref-api","doi"],"latest_commit_sha":null,"homepage":"","language":"Rust","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/mattsse.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE-APACHE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2019-02-23T09:40:39.000Z","updated_at":"2025-01-22T15:32:26.000Z","dependencies_parsed_at":"2024-10-23T08:25:36.519Z","dependency_job_id":"17d38abc-337c-470f-a9f5-7349e8a700fc","html_url":"https://github.com/mattsse/crossref-rs","commit_stats":{"total_commits":72,"total_committers":2,"mean_commits":36.0,"dds":0.01388888888888884,"last_synced_commit":"97829e8bbe251567c42660be7655a4c6891fabad"},"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/mattsse/crossref-rs","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mattsse%2Fcrossref-rs","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mattsse%2Fcrossref-rs/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mattsse%2Fcrossref-rs/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mattsse%2Fcrossref-rs/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/mattsse","download_url":"https://codeload.github.com/mattsse/crossref-rs/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mattsse%2Fcrossref-rs/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":263619742,"owners_count":23489558,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["api","crossref-api","doi"],"created_at":"2024-10-03T13:35:01.574Z","updated_at":"2025-07-04T21:05:05.776Z","avatar_url":"https://github.com/mattsse.png","language":"Rust","funding_links":[],"categories":[],"sub_categories":[],"readme":"Crossref-rs - A rust client for the Crossref-API\n=====================\n[![Build Status](https://travis-ci.com/MattsSe/crossref-rs.svg?branch=master)](https://travis-ci.com/MattsSe/crossref-rs)\n[![Crates.io](https://img.shields.io/crates/v/crossref.svg)](https://crates.io/crates/crossref)\n[![Documentation](https://docs.rs/crossref/badge.svg)](https://docs.rs/crossref)\n\n\n[Crossref API docs](https://github.com/CrossRef/rest-api-doc)\n\nThis client is inspired by [sckott/habanero](https://github.com/sckott/habanero/).\n\n\n`Crossref` - Crossref search API. The `Crossref` crate provides methods matching Crossref API routes:\n\n* `works` - `/works` route\n* `members` - `/members` route\n* `prefixes` - `/prefixes` route\n* `funders` - `/funders` route\n* `journals` - `/journals` route\n* `types` - `/types` route\n* `agency` - `/works/{doi}/agency` get DOI minting agency\n\n\n## Usage\n\n### Create a `Crossref` client:\n\n```rust\nlet client = Crossref::builder().build()?;\n```\n\nIf you have an [Authorization token for Crossref's Plus service](https://github.com/CrossRef/rest-api-doc#authorization-token-for-plus-service):\n\n```rust\nlet client = Crossref::builder()\n    .token(\"token\")\n    .build()?;\n```\n\nEncouraged to use the **The Polite Pool**:\n\n[Good manners = more reliable service](https://github.com/CrossRef/rest-api-doc#good-manners--more-reliable-service)\n\nTo get into Crossref's polite pool include a email address\n\n```rust\nlet client = Crossref::builder()\n     .polite(\"polite@example.com\")\n     .token(\"your token\")\n     .build()?;\n```\n\n### Constructing Queries\nNot all components support queries and there are custom available parameters for each route that supports querying.\nFor each resource components that supports querying there exist a Query struct: `WorksQuery`, `MembersQuery`, `FundersQuery`. The `WorksQuery` also differs from the others by supporting [deep paging with cursors](https://github.com/CrossRef/rest-api-doc#deep-paging-with-cursors) and [field queries](https://github.com/CrossRef/rest-api-doc#works-field-queries). \n\notherwise creating queries works the same for all resource components:\n\n```rust\n\nlet query = WorksQuery::new(\"Machine Learning\")\n    // field queries supported for `Works`\n    .field_query(FieldQuery::author(\"Some Author\"))\n    // filters are specific for each resource component\n    .filter(WorksFilter::HasOrcid)\n    .order(Order::Asc)\n    .sort(Sort::Score);\n```\n\n\n### Get Records\n\nSee [this table](https://github.com/CrossRef/rest-api-doc#resource-components) for a detailed overview of the major components.\n\nThere are 3 different targets:\n\n* **standalone resource components**: `/works`, `/members`, `funders`, `prefixes`, `types` that return a list list of the corresponding items and can be specified with queries\n* **Resource component with identifiers**: `/works/{doi}?\u003cquery\u003e`,`/members/{member_id}?\u003cquery\u003e`, etc. that returns a single item if found.\n* **combined with the `works` route**: The works component can be appended to other resources: `/members/{member_id}/works?\u003cquery\u003e` etc. that returns a list of matching `Work` items as `WorkList`.\n\nThis resembles in the enums of the resource components, eg. for `Members`:\n\n```rust\npub enum Members {\n    /// target a specific member at `/members/{id}`\n    Identifier(String),\n    /// target all members that match the query at `/members?query...`\n    Query(MembersQuery),\n    /// target a `Work` for a specific member at `/members/{id}/works?query..`\n    Works(WorksIdentQuery),\n}\n```\n\n### Examples\n\nAll options are supported by the client:\n\n**Query Single Item by DOI or ID**\n\nAnalogous methods exist for all resource components\n\n```rust\nlet work = client.work(\"10.1037/0003-066X.59.1.29\")?;\n\nlet agency = client.work_agency(\"10.1037/0003-066X.59.1.29\")?;\n\nlet funder = client.funder(\"funder_id\")?;\n\nlet member = client.member(\"member_id\")?;\n```\n\n**Query**\n\n```rust\nlet query = WorksQuery::new(\"Machine Learning\");\n\n// one page of the matching results\nlet works = client.works(query)?;\n```\n\nAlternatively insert a free form query term directly\n\n```rust\nlet works = client.works(\"Machine Learning\")?;\n```\n\n **Combining Routes with the `Works` route**\n\nFor each resource component other than `Works` there exist methods to append a `WorksQuery` with the ID option `/members/{member_id}/works?\u003cquery\u003e?`\n\n```\nuse crossref::*;\nfn run() -\u003e Result\u003c()\u003e {\n    let client = Crossref::builder().build()?;\n    let works = client.member_works(WorksQuery::new(\"machine learning\")\n    .sort(Sort::Score).into_ident(\"member_id\"))?;\n    Ok(())\n}\n```\n\nThis would be the same as using the [`Crossref::works`] method by supplying the combined type\n\n```rust\nuse crossref::*;\nfn run() -\u003e Result\u003c()\u003e {\n    let client = Crossref::builder().build()?;\n    let works = client.works(WorksQuery::new(\"machine learning\")\n     .sort(Sort::Score)\n     .into_combined_query::\u003cMembers\u003e(\"member_id\"))?;\n    Ok(())\n}\n```\n\n** Deep paging for `Works` **\n[Deep paging results](https://github.com/CrossRef/rest-api-doc#deep-paging-with-cursors)\nDeep paging is supported for all queries, that return a list of `Work`, `WorkList`.\nThis function returns a new iterator over pages of `Work`, which is returned as bulk of items as a `WorkList` by crossref.\nUsually a single page `WorkList` contains 20 items.\n\nExample\n\nIterate over all `Works` linked to search term `Machine Learning`\n\n```rust\nuse crossref::{Crossref, WorksQuery, Work};\nfn run() -\u003e Result\u003c(), crossref::Error\u003e {\n    let client = Crossref::builder().build()?;\n    \n    let all_works: Vec\u003cWork\u003e = client.deep_page(WorksQuery::new(\"Machine Learning\")).flat_map(|x|x.items).collect();\n    \n    Ok(())\n}\n```\n\nWhich can be simplified to\n```rust\nuse crossref::{Crossref, WorksQuery, Work};\nfn run() -\u003e Result\u003c(), crossref::Error\u003e {\n    let client = Crossref::builder().build()?;\n    \n    let all_works: Vec\u003cWork\u003e = client.deep_page(\"Machine Learning\").into_work_iter().collect();\n    \n    Ok(())\n}\n```\n\n\nIterate over all the pages (`WorkList`) of the funder with id `funder id` by using a combined query.\nA single `WorkList` usually holds 20 `Work` items.\n\n```rust\nuse crossref::{Crossref, Funders, WorksQuery, Work, WorkList};\nfn run() -\u003e Result\u003c(), crossref::Error\u003e {\n    let client = Crossref::builder().build()?;\n    \n    let all_funder_work_list: Vec\u003cWorkList\u003e = client.deep_page(WorksQuery::default()\n            .into_combined_query::\u003cFunders\u003e(\"funder id\")\n      )\n        .collect();\n    \n    Ok(())\n}\n```\n\nIterate over all `Work` items of a specfic funder directly.\n\n```rust\nuse crossref::{Crossref, Funders, WorksQuery, Work, WorkList};\nfn run() -\u003e Result\u003c(), crossref::Error\u003e {\n    let client = Crossref::builder().build()?;\n    \n    let all_works: Vec\u003cWork\u003e = client.deep_page(WorksQuery::default()\n         .into_combined_query::\u003cFunders\u003e(\"funder id\"))\n         .into_work_iter()\n         .collect();\n    \n    Ok(())\n}\n```\n\n\n## Command Line Application\n\n### Installation\n```shell\ncargo install crossref --features cli\n```\n\n### Usage\n\nTop level subcommands\n```text\nUSAGE:\n    crossref \u003cSUBCOMMAND\u003e\n\nFLAGS:\n    -h, --help       Prints help information\n    -V, --version    Prints version information\n\nSUBCOMMANDS:\n    funders     Query crossref funders\n    help        Prints this message or the help of the given subcommand(s)\n    journals    Query crossref journals\n    members     Query crossref members\n    prefixes    Query crossref prefixes\n    types       Query crossref types\n    works       Query crossref works\n\n```\n\nAdditional options for the component subcommands (querying, sorting, ordering and limiting is only supported for subcommands \u003cworks|funders|members\u003e and is overridden by a present `--id` options)\n\n```text\nUSAGE:\n    crossref works [FLAGS] [OPTIONS] [SUBCOMMAND]\n\nFLAGS:\n    -a, --append       if the output file already exists, append instead of overwriting the file\n    -d, --deep-page    Enable deep paging. If a limit is set, then the limit takes priority.\n    -h, --help         Prints help information\n    -s, --silent       do not print anything\n    -V, --version      Prints version information\n\nOPTIONS:\n    -i, --id \u003cid\u003e                    The id of component.\n    -l, --limit \u003climit\u003e              limit the amount of results\n        --offset \u003coffset\u003e            Sets an offset where crossref begins to retrieve items.\n        --order \u003corder\u003e              How to order the results: asc or desc\n    -o \u003coutput\u003e                      output path where the results shall be stored\n        --polite \u003cpolite\u003e            The email to use to get into crossref's polite pool\n    -q, --query \u003cquery_terms\u003e...     The free form terms for the query\n        --sample \u003csample\u003e            Request randoms Elements. Overrides all other options.\n        --sort \u003csort\u003e                How to sort the results, such as updated, indexed, published, issued\n        --token \u003ctoken\u003e              The token to use for the crossref client\n        --user-agent \u003cuser_agent\u003e    The user agent to use for the crossref client\n```\n\n### Examples\n\nRetrieve a specific work by a doi\n\n```shell\n crossref works --id \"10.1037/0003-066X.59.1.29\"\n```\n\nSave the results as json\n\n```shell\n crossref works --id \"10.1037/0003-066X.59.1.29\" -o output.json\n```\n\nRetrieve any other components by their ids\n\n```shell\n crossref \u003cworks|journals|members|prefixes|types\u003e --id \"10.1037/0003-066X.59.1.29\" -o output.json\n```\n\nSome components support additional filtering\n\n```\ncrossref \u003cworks|funders|members\u003e --query \"A search term such as `Machine learning` for works\" --limit 10 --offset 200 --order asc\n```\n\nGet `Works` of a specific component, such as a member with the id `98`:\n\n```\ncrossref works member 98\n```\n\n`\u003cprefix|funder|prefix|type` are also supported in the same way.\n\n\nBy default deep paging is disabled, hence the max amount of results of `Works` will be 20 (a single crossref page).\nBy enabling the `--deep-page` flag, all available results will be gathered.\n\nTo get in to the polite pool supply your email to the request headers with `--polite \"polite@example.com\"`\n\n## License\n\nLicensed under either of these:\n\n * Apache License, Version 2.0, ([LICENSE-APACHE](LICENSE-APACHE) or\n   https://www.apache.org/licenses/LICENSE-2.0)\n * MIT license ([LICENSE-MIT](LICENSE-MIT) or\n   https://opensource.org/licenses/MIT)\n   \n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmattsse%2Fcrossref-rs","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmattsse%2Fcrossref-rs","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmattsse%2Fcrossref-rs/lists"}