diff --git a/NAMESPACE b/NAMESPACE index a700567e..60c61c21 100644 --- a/NAMESPACE +++ b/NAMESPACE @@ -2,6 +2,12 @@ export(affiliations) export(beneficiary_enrollment) +export(by_geography) +export(by_geography_years) +export(by_provider) +export(by_provider_years) +export(by_service) +export(by_service_years) export(cc_multiple) export(cc_multiple_years) export(cc_specific) @@ -9,18 +15,12 @@ export(cc_specific_years) export(clinicians) export(hospitals) export(missing_information) -export(nppes_npi) +export(nppes) export(open_payments) export(open_payments_years) export(opt_out) export(order_refer) export(pending_applications) -export(physician_by_geography) -export(physician_by_geography_years) -export(physician_by_provider) -export(physician_by_provider_years) -export(physician_by_service) -export(physician_by_service_years) export(providers) export(quality_eligibility) export(quality_payment) diff --git a/R/globals.R b/R/globals.R index c164efea..46f3e8a9 100644 --- a/R/globals.R +++ b/R/globals.R @@ -173,37 +173,26 @@ utils::globalVariables(c( "NPI", # "last_name", # "first_name", # - "y", # - "number", # - "enumeration_type", # - "addresses", # - "taxonomies", # - "practiceLocations", # - "other_names", # - "practice_locations", # - "country_code", # - "telephone_number", # - "postal_code", # - "address_purpose", # - "address_1", # - "purpose", # - "code", # - "desc", # - "taxonomy_group", # - "primary", # - "issuer", # - "identifier", # - "y", # - "number", # - "enumeration_type", # - "basic", # - "addresses", # - "taxonomies", # - "enumeration_date", # - "address_purpose", # - "country_name", # - "telephone_number", # - "postal_code", # + "y", # + "number", # + "enumeration_type", # + "addresses", # + "taxonomies", # + "practiceLocations", # + "other_names", # + "practice_locations", # + "country_code", # + "telephone_number", # + "postal_code", # + "address_purpose", # + "address_1", # + "purpose", # + "code", # + "desc", # + "taxonomy_group", # + "primary", # + "issuer", # + "identifier", # "data_lists", # "outcome", # "description", # @@ -336,121 +325,123 @@ utils::globalVariables(c( "distro", # "y", # "y", # - "distro", # - "y", # - "rndrng_prvdr_geo_lvl", # - "rndrng_prvdr_geo_desc", # - "rndrng_prvdr_geo_cd", # - "hcpcs_cd", # - "hcpcs_drug_ind", # - "tot_rndrng_prvdrs", # - "tot_benes", # - "tot_srvcs", # - "tot_bene_day_srvcs", # - "avg_sbmtd_chrg", # - "avg_mdcr_alowd_amt", # - "avg_mdcr_pymt_amt", # - "avg_mdcr_stdzd_amt", # - "distro", # - "y", # - "rndrng_prvdr_crdntls", # - "rndrng_prvdr_mdcr_prtcptg_ind", # - "rndrng_npi", # - "rndrng_prvdr_first_name", # - "rndrng_prvdr_mi", # - "rndrng_prvdr_last_org_name", # - "rndrng_prvdr_gndr", # - "rndrng_prvdr_ent_cd", # - "street", # - "rndrng_prvdr_city", # - "rndrng_prvdr_state_abrvtn", # - "rndrng_prvdr_state_fips", # - "rndrng_prvdr_zip5", # - "rndrng_prvdr_ruca", # - "rndrng_prvdr_cntry", # - "rndrng_prvdr_type", # - "tot_hcpcs_cds", # - "tot_benes", # - "tot_srvcs", # - "tot_sbmtd_chrg", # - "tot_mdcr_alowd_amt", # - "tot_mdcr_pymt_amt", # - "tot_mdcr_stdzd_amt", # - "drug_tot_hcpcs_cds", # - "drug_tot_benes", # - "drug_tot_srvcs", # - "drug_sbmtd_chrg", # - "drug_mdcr_alowd_amt", # - "drug_mdcr_pymt_amt", # - "drug_mdcr_stdzd_amt", # - "med_tot_hcpcs_cds", # - "med_tot_benes", # - "med_tot_srvcs", # - "med_sbmtd_chrg", # - "med_mdcr_alowd_amt", # - "med_mdcr_pymt_amt", # - "med_mdcr_stdzd_amt", # - "bene_avg_age", # - "bene_age_lt_65_cnt", # - "bene_age_65_74_cnt", # - "bene_age_75_84_cnt", # - "bene_age_gt_84_cnt", # - "bene_feml_cnt", # - "bene_male_cnt", # - "bene_race_wht_cnt", # - "bene_race_black_cnt", # - "bene_race_api_cnt", # - "bene_race_hspnc_cnt", # - "bene_race_nat_ind_cnt", # - "bene_race_othr_cnt", # - "bene_dual_cnt", # - "bene_ndual_cnt", # - "bene_cc_af_pct", # - "bene_cc_alzhmr_pct", # - "bene_cc_asthma_pct", # - "bene_cc_cncr_pct", # - "bene_cc_chf_pct", # - "bene_cc_ckd_pct", # - "bene_cc_copd_pct", # - "bene_cc_dprssn_pct", # - "bene_cc_dbts_pct", # - "bene_cc_hyplpdma_pct", # - "bene_cc_hyprtnsn_pct", # - "bene_cc_ihd_pct", # - "bene_cc_opo_pct", # - "bene_cc_raoa_pct", # - "bene_cc_sz_pct", # - "bene_cc_strok_pct", # - "bene_avg_risk_scre", # - "entity_type", # - "distro", # - "y", # - "tot_benes", # - "tot_srvcs", # - "tot_bene_day_srvcs", # - "rndrng_npi", # - "rndrng_prvdr_ent_cd", # - "rndrng_prvdr_first_name", # - "rndrng_prvdr_mi", # - "rndrng_prvdr_last_org_name", # - "rndrng_prvdr_crdntls", # - "rndrng_prvdr_gndr", # - "rndrng_prvdr_type", # - "street", # - "rndrng_prvdr_city", # - "rndrng_prvdr_state_abrvtn", # - "rndrng_prvdr_state_fips", # - "rndrng_prvdr_zip5", # - "rndrng_prvdr_ruca", # - "rndrng_prvdr_cntry", # - "rndrng_prvdr_mdcr_prtcptg_ind", # - "hcpcs_cd", # - "hcpcs_desc", # - "hcpcs_drug_ind", # - "avg_sbmtd_chrg", # - "avg_mdcr_alowd_amt", # - "avg_mdcr_pymt_amt", # - "avg_mdcr_stdzd_amt", # + "distro", # + "y", # + "rndrng_prvdr_geo_lvl", # + "rndrng_prvdr_geo_desc", # + "rndrng_prvdr_geo_cd", # + "hcpcs_cd", # + "hcpcs_drug_ind", # + "place_of_srvc", # + "tot_rndrng_prvdrs", # + "tot_benes", # + "tot_srvcs", # + "tot_bene_day_srvcs", # + "avg_sbmtd_chrg", # + "avg_mdcr_alowd_amt", # + "avg_mdcr_pymt_amt", # + "avg_mdcr_stdzd_amt", # + "distro", # + "y", # + "rndrng_prvdr_crdntls", # + "rndrng_prvdr_mdcr_prtcptg_ind", # + "rndrng_npi", # + "rndrng_prvdr_first_name", # + "rndrng_prvdr_mi", # + "rndrng_prvdr_last_org_name", # + "rndrng_prvdr_gndr", # + "rndrng_prvdr_ent_cd", # + "street", # + "rndrng_prvdr_city", # + "rndrng_prvdr_state_abrvtn", # + "rndrng_prvdr_state_fips", # + "rndrng_prvdr_zip5", # + "rndrng_prvdr_ruca", # + "rndrng_prvdr_cntry", # + "rndrng_prvdr_type", # + "tot_hcpcs_cds", # + "tot_benes", # + "tot_srvcs", # + "tot_sbmtd_chrg", # + "tot_mdcr_alowd_amt", # + "tot_mdcr_pymt_amt", # + "tot_mdcr_stdzd_amt", # + "drug_tot_hcpcs_cds", # + "drug_tot_benes", # + "drug_tot_srvcs", # + "drug_sbmtd_chrg", # + "drug_mdcr_alowd_amt", # + "drug_mdcr_pymt_amt", # + "drug_mdcr_stdzd_amt", # + "med_tot_hcpcs_cds", # + "med_tot_benes", # + "med_tot_srvcs", # + "med_sbmtd_chrg", # + "med_mdcr_alowd_amt", # + "med_mdcr_pymt_amt", # + "med_mdcr_stdzd_amt", # + "bene_avg_age", # + "bene_age_lt_65_cnt", # + "bene_age_65_74_cnt", # + "bene_age_75_84_cnt", # + "bene_age_gt_84_cnt", # + "bene_feml_cnt", # + "bene_male_cnt", # + "bene_race_wht_cnt", # + "bene_race_black_cnt", # + "bene_race_api_cnt", # + "bene_race_hspnc_cnt", # + "bene_race_nat_ind_cnt", # + "bene_race_othr_cnt", # + "bene_dual_cnt", # + "bene_ndual_cnt", # + "bene_cc_af_pct", # + "bene_cc_alzhmr_pct", # + "bene_cc_asthma_pct", # + "bene_cc_cncr_pct", # + "bene_cc_chf_pct", # + "bene_cc_ckd_pct", # + "bene_cc_copd_pct", # + "bene_cc_dprssn_pct", # + "bene_cc_dbts_pct", # + "bene_cc_hyplpdma_pct", # + "bene_cc_hyprtnsn_pct", # + "bene_cc_ihd_pct", # + "bene_cc_opo_pct", # + "bene_cc_raoa_pct", # + "bene_cc_sz_pct", # + "bene_cc_strok_pct", # + "bene_avg_risk_scre", # + "entity_type", # + "distro", # + "y", # + "tot_benes", # + "tot_srvcs", # + "tot_bene_day_srvcs", # + "rndrng_npi", # + "rndrng_prvdr_ent_cd", # + "rndrng_prvdr_first_name", # + "rndrng_prvdr_mi", # + "rndrng_prvdr_last_org_name", # + "rndrng_prvdr_crdntls", # + "rndrng_prvdr_gndr", # + "rndrng_prvdr_type", # + "street", # + "rndrng_prvdr_city", # + "rndrng_prvdr_state_abrvtn", # + "rndrng_prvdr_state_fips", # + "rndrng_prvdr_zip5", # + "rndrng_prvdr_ruca", # + "rndrng_prvdr_cntry", # + "rndrng_prvdr_mdcr_prtcptg_ind", # + "hcpcs_cd", # + "hcpcs_desc", # + "hcpcs_drug_ind", # + "place_of_srvc", # + "avg_sbmtd_chrg", # + "avg_mdcr_alowd_amt", # + "avg_mdcr_pymt_amt", # + "avg_mdcr_stdzd_amt", # "distro", # "y", # "pecos_asct_cntl_id", # diff --git a/R/hospitals.R b/R/hospitals.R index 4b76f0d7..ea17bec0 100644 --- a/R/hospitals.R +++ b/R/hospitals.R @@ -9,7 +9,7 @@ #' ### Links: #' - [Hospital Enrollments](https://data.cms.gov/provider-characteristics/hospitals-and-other-facilities/hospital-enrollments) #' -#' Update Frequency: **Monthly** +#' *Update Frequency:* **Monthly** #' #' @param npi Hospital’s National Provider Identifier #' @param facility_ccn Hospital’s CMS Certification Number (CCN) diff --git a/R/missing_information.R b/R/missing_information.R index 9878cb06..b6d05020 100644 --- a/R/missing_information.R +++ b/R/missing_information.R @@ -27,25 +27,26 @@ #' #' @return A [tibble][tibble::tibble-package] containing the search results. #' -#' @seealso [nppes_npi()] +#' @seealso [nppes()] #' #' @examples -#' # A provider that appears in the search results of the Missing Information -#' # API has no Endpoints entered into the NPPES NPI Registry and vice versa. +#' # A provider that appears in the search results +#' # of the Missing Information API has no Endpoints +#' # entered into the NPPES NPI Registry and vice versa. #' #' ## Appears #' missing_information(name = "Clouse, John") #' #' ## No Endpoints in NPPES -#' nppes_npi(npi = 1144224569, -#' tidy = FALSE) |> -#' dplyr::select(endpoints) +#' nppes(npi = 1144224569, +#' tidy = FALSE) |> +#' dplyr::select(endpoints) #' #' ## Does Not Appear #' missing_information(npi = 1003000423) #' #' ## Has Endpoints in NPPES -#' nppes_npi(npi = 1003000423, tidy = FALSE) |> +#' nppes(npi = 1003000423, tidy = FALSE) |> #' dplyr::select(endpoints) |> #' tidyr::unnest(cols = c(endpoints)) |> #' janitor::clean_names() |> diff --git a/R/nppes_npi.R b/R/nppes.R similarity index 59% rename from R/nppes_npi.R rename to R/nppes.R index f6787e56..1db7ae4b 100644 --- a/R/nppes_npi.R +++ b/R/nppes.R @@ -1,35 +1,29 @@ -#' Search the NPPES National Provider Identifier Registry API +#' National Registry of All Health Care Providers #' -#' @description `nppes_npi()` allows you to search the NPPES NPI -#' Registry's public API by many of the parameters defined in the -#' API's documentation. +#' @description +#' `nppes()` allows you to search the National Plan and Provider Enumeration +#' System (NPPES) NPI Registry's public API. Th Registry is a free directory of +#' all active National Provider Identifier (NPI) records. #' -#' @details The NPPES NPI Registry Public Search is a free directory of all -#' active National Provider Identifier (NPI) records. Healthcare providers -#' acquire their unique 10-digit NPIs to identify themselves in a standard -#' way throughout their industry. After CMS supplies an NPI, they publish -#' the parts of the NPI record that have public relevance, including the -#' provider’s name, taxonomy and practice address. It enables you to search -#' for providers in the NPPES (National Plan and Provider Enumeration -#' System.) All information produced by the NPI Registry is provided in -#' accordance with the NPPES Data Dissemination Notice. There is no charge -#' to use the NPI Registry. +#' ## National Provider Identifier (NPI) +#' Healthcare providers acquire their unique 10-digit NPIs to identify +#' themselves in a standard way throughout their industry. Once CMS supplies +#' an NPI, they publish the parts of the NPI record that have public relevance, +#' including the provider’s name, taxonomy and practice address. #' -#' ## Links -#' * [NPPES NPI Registry API Documentation](https://npiregistry.cms.hhs.gov/api-page) -#' * [NPPES NPI Registry API Demo](https://npiregistry.cms.hhs.gov/demo-api) +#' ### Links +#' - [NPPES NPI Registry API Documentation](https://npiregistry.cms.hhs.gov/api-page) +#' - [NPPES NPI Registry API Demo](https://npiregistry.cms.hhs.gov/demo-api) +#' +#' *Update Frequency:* **Weekly** #' -#' @source Centers for Medicare & Medicaid Services -#' @note Update Frequency: **Weekly** #' @param npi 10-digit National Provider Identifier (NPI). -#' @param entype Choices are either `I` for an Individual provider (NPI-1 or -#' Type 1) or `O` for an Organizational provider (NPI-2 or Type 2.). When -#' not specified, both Type 1 and Type 2 NPIs will be returned. Entype -#' cannot be the only criteria entered. -#' @param first_name Individual provider's (NPI-1) first name. Trailing wildcard +#' @param entype Entity type. Choices are either `I` for an Individual provider +#' or `O` for an Organizational provider. Cannot be the only criteria entered. +#' @param first_name Individual provider's first name. Trailing wildcard #' entries are permitted requiring at least two characters to be entered #' (e.g. `jo*` ). -#' @param last_name Individual provider's (NPI-1) last name. Trailing wildcard +#' @param last_name Individual provider's last name. Trailing wildcard #' entries are permitted requiring at least two characters to be entered #' (e.g. `jo*` ). #' @param purpose_name Refers to whether the name information entered pertains @@ -70,20 +64,20 @@ #' @return A [tibble][tibble::tibble-package] containing the search results. #' @autoglobal #' @export -nppes_npi <- function(npi = NULL, - entype = NULL, - first_name = NULL, - last_name = NULL, - org_name = NULL, - purpose_name = NULL, - taxonomy_desc = NULL, - city = NULL, - state = NULL, - zipcode = NULL, - country = NULL, - limit = 1200, - skip = NULL, - tidy = TRUE) { +nppes <- function(npi = NULL, + entype = NULL, + first_name = NULL, + last_name = NULL, + org_name = NULL, + purpose_name = NULL, + taxonomy_desc = NULL, + city = NULL, + state = NULL, + zipcode = NULL, + country = NULL, + limit = 1200, + skip = NULL, + tidy = TRUE) { if (!is.null(npi)) {npi_check(npi)} if (!is.null(entype)) {entype <- entype_arg(entype)} @@ -356,290 +350,6 @@ nppes_npi <- function(npi = NULL, return(results) } -#' Search the NPPES National Provider Identifier Registry API -#' -#' @description `nppes_npi()` allows you to search the NPPES NPI -#' Registry's public API by many of the parameters defined in the -#' API's documentation. -#' -#' @details The NPPES NPI Registry Public Search is a free directory of all -#' active National Provider Identifier (NPI) records. Healthcare providers -#' acquire their unique 10-digit NPIs to identify themselves in a standard -#' way throughout their industry. After CMS supplies an NPI, they publish -#' the parts of the NPI record that have public relevance, including the -#' provider’s name, taxonomy and practice address. It enables you to search -#' for providers in the NPPES (National Plan and Provider Enumeration -#' System.) All information produced by the NPI Registry is provided in -#' accordance with the NPPES Data Dissemination Notice. There is no charge -#' to use the NPI Registry. -#' -#' ## Links -#' * [NPPES NPI Registry API Documentation](https://npiregistry.cms.hhs.gov/api-page) -#' * [NPPES NPI Registry API Demo](https://npiregistry.cms.hhs.gov/demo-api) -#' -#' @source Centers for Medicare & Medicaid Services -#' @note Update Frequency: **Weekly** -#' @param npi 10-digit National Provider Identifier (NPI). -#' @param entype The Read API can be refined to retrieve only Individual -#' Providers (`NPI-1` or Type 1) or Organizational Providers (`NPI-2` or -#' Type 2.) When not specified, both Type 1 and Type 2 NPIs will be -#' returned. When using the Enumeration Type, it cannot be the only -#' criteria entered. Additional criteria must also be entered as well. -#' @param first_name Provider's first name. Applies to -#' **Individual Providers (NPI-1)** only. Trailing wildcard entries are -#' permitted requiring at least two characters to be entered (e.g. "jo*" ). -#' This field allows the following special characters: ampersand(`&`), -#' apostrophe(`,`), colon(`:`), comma(`,`), forward slash(`/`), -#' hyphen(`-`), left and right parentheses(`()`), period(`.`), -#' pound sign(`#`), quotation mark(`"`), and semi-colon(`;`). -#' @param last_name Provider's last name. Applies to -#' **Individual Providers (NPI-1)** only. Trailing wildcard entries are -#' permitted requiring at least two characters to be entered (e.g. "jo*" ). -#' This field allows the following special characters: ampersand(`&`), -#' apostrophe(`,`), colon(`:`), comma(`,`), forward slash(`/`), -#' hyphen(`-`), left and right parentheses(`()`), period(`.`), -#' pound sign(`#`), quotation mark(`"`), and semi-colon(`;`). -#' @param org_name Healthcare organization's name. Applies to -#' **Organizational Providers (NPI-2)** only. Trailing wildcard entries are -#' permitted requiring at least two characters to be entered. All types of -#' Organization Names (LBN, DBA, Former LBN, Other Name) associated with an -#' NPI are examined for matching contents, therefore, the results might -#' contain an organization name different from the one entered in the -#' Organization Name criterion. This field allows the following special -#' characters: ampersand, apostrophe, "at" sign, colon, comma, forward -#' slash, hyphen, left and right parentheses, period, pound sign, quotation -#' mark, and semi-colon. -#' @param taxonomy_desc Search for providers by their taxonomy by entering the -#' taxonomy description. -#' @param city City associated with the provider's address. To search for a -#' Military Address, enter either `APO` or `FPO` into the City field. -#' This field allows the following special characters: ampersand, -#' apostrophe, colon, comma, forward slash, hyphen, left and right -#' parentheses, period, pound sign, quotation mark, and semi-colon. -#' @param state State abbreviation associated with the provider's address. -#' This field **cannot** be used as the only input criterion. If this -#' field is used, at least one other field, besides the `prov_type` and -#' `country`, must be populated. Valid values for state abbreviations: -#' \url{https://npiregistry.cms.hhs.gov/help-api/state}. -#' @param zipcode The Postal Code associated with the provider's address -#' identified in Address Purpose. If you enter a 5 digit postal code, it -#' will match any appropriate 9 digit (zip+4) codes in the data. Trailing -#' wildcard entries are permitted requiring at least two characters to be -#' entered (e.g., "21*"). -#' @param country Country abbreviation associated with the provider's -#' address. This field **can** be used as the only input criterion, as long -#' as the value selected *is not* **US** (United States). Valid values for -#' country abbreviations: -#' \url{https://npiregistry.cms.hhs.gov/help-api/country}. -#' @param limit Maximum number of results to return; -#' default is 200, maximum is 1200. -#' @param skip Number of results to skip after searching -#' the previous number; set in `limit`. -#' @param tidy Tidy output; default is `TRUE`. -#' @examplesIf interactive() -#' nppes_npi(npi = 1528060837) -#' @return A [tibble][tibble::tibble-package] containing the search results. -#' @autoglobal -#' @noRd -nppes_summary <- function(npi = NULL, - entype = NULL, - first_name = NULL, - last_name = NULL, - org_name = NULL, - taxonomy_desc = NULL, - city = NULL, - state = NULL, - zipcode = NULL, - country = NULL, - limit = 1200, - skip = NULL, - tidy = FALSE) { - - # request and response ---------------------------------------------------- - request <- httr2::request("https://npiregistry.cms.hhs.gov/api/?version=2.1") |> - httr2::req_url_query(number = npi, - enumeration_type = entype, - first_name = first_name, - last_name = last_name, - organization_name = org_name, - taxonomy_description = taxonomy_desc, - city = city, - state = state, - postal_code = zipcode, - country_code = country, - limit = limit, - skip = skip) |> - httr2::req_perform() - - # parse response --------------------------------------------------------- - response <- httr2::resp_body_json(request, check_type = FALSE, simplifyVector = TRUE) - - res_cnt <- response$result_count - - # no search results returns empty tibble ---------------------------------- - if (is.null(res_cnt) | res_cnt == 0) { - - cli_args <- tibble::tribble( - ~x, ~y, - "npi", as.character(npi), - "entype", entype, - "first_name", first_name, - "last_name", last_name, - "org_name", org_name, - "taxonomy_desc", taxonomy_desc, - "city", city, - "state", state, - "zipcode", as.character(zipcode), - "country", country) |> - tidyr::unnest(cols = c(y)) - - cli_args <- purrr::map2(cli_args$x, - cli_args$y, - stringr::str_c, - sep = ": ", - collapse = "") - - cli::cli_alert_danger("No results for {.val {cli_args}}", wrap = TRUE) - return(invisible(NULL)) - } - - results <- response$results |> dplyr::tibble() - - if (tidy) { - - # basic ------------------------------------------------------------------ - - results <- results |> - dplyr::select(npi = number, - entype = enumeration_type, - basic, - addresses, - taxonomy = taxonomies) |> - tidyr::unnest(basic) |> - dplyr::mutate(dplyr::across(dplyr::contains("date"), ~parsedate::parse_date(.)), - dplyr::across(dplyr::contains("date"), ~lubridate::ymd(.)), - dplyr::across(dplyr::where(is.character), ~dplyr::na_if(., "")), - dplyr::across(dplyr::where(is.character), ~dplyr::na_if(., "N/A")), - dplyr::across(dplyr::where(is.character), ~dplyr::na_if(., "--")), - dplyr::across(dplyr::where(is.character), ~clean_credentials(.)), - enumeration_duration = lubridate::as.duration(lubridate::today() - enumeration_date), - entype = entype_char(entype), - dplyr::across(dplyr::any_of(c("sole_proprietor", "organizational_subpart")), ~yn_logical(.))) - - # replace empty lists with NA ------------------------------------------- - results[apply(results, 2, function(x) lapply(x, length) == 0)] <- NA - - # addresses -------------------------------------------------------------- - address <- results |> - dplyr::select(npi, addresses) |> - tidyr::unnest(addresses) |> - tidyr::unite("street", - dplyr::any_of(c("address_1", "address_2")), - remove = TRUE, - na.rm = TRUE, - sep = " ") |> - dplyr::mutate(address_purpose = tolower(address_purpose), - address_type = NULL, - country_code = NULL) |> - dplyr::rename(country = country_name, - phone_number = telephone_number, - zipcode = postal_code) |> - dplyr::filter(address_purpose == "location") |> - dplyr::select(!address_purpose) - - # tidyr::pivot_wider(id_cols = dplyr::any_of(c("npi", "country")), - # names_from = address_purpose, - # values_from = dplyr::any_of(c("street", "city", - # "state", "zipcode", - # "phone", "fax")), - # names_glue = "{address_purpose}_{.value}") - - results <- results |> - dplyr::select(!addresses) |> - dplyr::left_join(address, dplyr::join_by(npi)) - - ## Some taxonomies are all labelled - ## primary = FALSE nppes_npi(npi = 1558364273) - - # tidyr::unnest(taxonomy, names_sep = "_") |> - # dplyr::filter(taxonomy_primary == TRUE) |> - # dplyr::select(!c(taxonomy_taxonomy_group, taxonomy_primary)) |> - # janitor::remove_empty(which = c("rows", "cols")) - - valid_fields <- c("npi", - "entype", - "enumeration_date", - "enumeration_duration", - "last_updated", - "certification_date", - "status", - "organization_name", - "organizational_subpart", - "first_name", - "middle_name", - "last_name", - "credential", - "gender", - "sole_proprietor", - "country", - "street", - "city", - "state", - "zipcode", - "phone_number", - "fax_number", - "taxonomy_code", - "taxonomy_desc", - "taxonomy_state", - "taxonomy_license") - - results <- results |> - dplyr::select(dplyr::any_of(valid_fields)) - - } - return(results) -} - -#' Search the NPPES National Provider Identifier Registry API -#' -#' @description `nppes_npi_multi()` allows you to search the NPPES NPI -#' Registry's public API by many of the parameters defined in the -#' API's documentation. -#' -#' @details The NPPES NPI Registry Public Search is a free directory of all -#' active National Provider Identifier (NPI) records. Healthcare providers -#' acquire their unique 10-digit NPIs to identify themselves in a standard -#' way throughout their industry. After CMS supplies an NPI, they publish -#' the parts of the NPI record that have public relevance, including the -#' provider’s name, taxonomy and practice address. It enables you to search -#' for providers in the NPPES (National Plan and Provider Enumeration -#' System.) All information produced by the NPI Registry is provided in -#' accordance with the NPPES Data Dissemination Notice. There is no charge -#' to use the NPI Registry. -#' -#' ## Links -#' * [NPPES NPI Registry API Documentation](https://npiregistry.cms.hhs.gov/api-page) -#' * [NPPES NPI Registry API Demo](https://npiregistry.cms.hhs.gov/demo-api) -#' -#' @source Centers for Medicare & Medicaid Services -#' @note Update Frequency: **Weekly** -#' @param df data frame, tibble -#' @autoglobal -#' @noRd -nppes_npi_multi <- function(df) { - - npis <- df |> - tibble::deframe() |> - as.list() - - results <- npis |> - purrr::map(nppes_npi) |> - dplyr::bind_rows() - - return(results) -} - - #' Search the NPPES National Provider Identifier Registry API #' #' @description `nppes_npi()` allows you to search the NPPES NPI diff --git a/R/physician_by_geography.R b/R/physician_by_geography.R index 6c1c42c2..027e4ae8 100644 --- a/R/physician_by_geography.R +++ b/R/physician_by_geography.R @@ -14,13 +14,12 @@ #' a HCPCS drug indicator to identify whether the HCPCS product/service is #' a drug as defined from the Medicare Part B Drug ASP list. #' -#' ## Links -#' * [Medicare Physician & Other Practitioners: by Geography and Service API](https://data.cms.gov/provider-summary-by-type-of-service/medicare-physician-other-practitioners/medicare-physician-other-practitioners-by-geography-and-service) +#' ### Links +#' - [Medicare Physician & Other Practitioners: by Geography and Service API](https://data.cms.gov/provider-summary-by-type-of-service/medicare-physician-other-practitioners/medicare-physician-other-practitioners-by-geography-and-service) #' -#' @source Centers for Medicare & Medicaid Services #' @note Update Frequency: **Annually** -#' @param year year int (required); Year in YYYY format. Run helper function -#' `provider:::physician_by_geography_years()` to return a vector of the years +#' @param year int (required); Year in YYYY format. Run helper function +#' `by_geography_years()` to return a vector of the years #' currently available. #' @param level Identifies the level of geography by which the data in the #' row has been aggregated. A value of 'State' indicates the data in the @@ -48,15 +47,17 @@ #' restrictions, the CMS Level II descriptions have been truncated to #' 256 bytes. As a result, the same HCPCS description can be associated #' with more than one HCPCS code. -#' @param hcpcs_drug Flag that identifies whether the HCPCS code for the specific +#' @param drug Flag that identifies whether the HCPCS code for the specific #' service furnished by the provider is a HCPCS listed on the Medicare Part #' B Drug Average Sales Price (ASP) File. -#' @param place_of_srvc Identifies whether the place of service submitted on the claims +#' @param pos Identifies whether the place of service submitted on the claims #' is a facility (`facility`) or non-facility (`office`). Non-facility #' is generally an office setting; however other entities are included #' in non-facility. #' @param tidy Tidy output; default is `TRUE`. +#' #' @return A [tibble][tibble::tibble-package] containing the search results. +#' #' @examplesIf interactive() #' physician_by_geography(hcpcs_code = "0002A", year = 2020) #' service <- purrr::map_dfr(as.character(2013:2020), @@ -77,25 +78,23 @@ #' # State Level #' purrr::map2_dfr(arg_cross$x, arg_cross$y, #' ~physician_by_geography(geo_level = "Georgia", year = .x, hcpcs_code = .y)) -#' @rdname provider-statistics #' @autoglobal #' @export -physician_by_geography <- function(year, - level = NULL, - sublevel = NULL, - fips = NULL, - hcpcs_code = NULL, - hcpcs_desc = NULL, - hcpcs_drug = NULL, - place_of_srvc = NULL, - tidy = TRUE) { - - if (!is.null(place_of_srvc)) {place_of_srvc <- pos_char(place_of_srvc)} - - # match args ---------------------------------------------------- +by_geography <- function(year, + level = NULL, + sublevel = NULL, + fips = NULL, + hcpcs_code = NULL, + hcpcs_desc = NULL, + drug = NULL, + pos = NULL, + tidy = TRUE) { + + if (!is.null(pos)) {pos <- pos_char(pos)} + rlang::check_required(year) year <- as.character(year) - rlang::arg_match(year, values = as.character(physician_by_geography_years())) + rlang::arg_match(year, values = as.character(by_geography_years())) # update distribution ids ------------------------------------------------- id <- cms_update(api = "Medicare Physician & Other Practitioners - by Geography and Service", @@ -111,8 +110,8 @@ physician_by_geography <- function(year, "Rndrng_Prvdr_Geo_Cd", fips, "HCPCS_Cd", hcpcs_code, "HCPCS_Desc", hcpcs_desc, - "HCPCS_Drug_Ind", hcpcs_drug, - "Place_Of_Srvc", place_of_srvc) + "HCPCS_Drug_Ind", drug, + "Place_Of_Srvc", pos) # map param_format and collapse ------------------------------------------- @@ -140,8 +139,8 @@ physician_by_geography <- function(year, "fips", as.character(fips), "hcpcs_code", as.character(hcpcs_code), "hcpcs_desc", hcpcs_desc, - "hcpcs_drug", as.character(hcpcs_drug), - "place_of_srvc", place_of_srvc) |> + "drug", as.character(drug), + "pos", pos) |> tidyr::unnest(cols = c(y)) cli_args <- purrr::map2(cli_args$x, @@ -161,7 +160,7 @@ physician_by_geography <- function(year, # clean names ------------------------------------------------------------- if (tidy) { - results <- dplyr::rename_with(results, str_to_snakecase) |> + results <- janitor::clean_names(results) |> dplyr::mutate(year = as.integer(year)) |> dplyr::select(year, level = rndrng_prvdr_geo_lvl, @@ -169,19 +168,19 @@ physician_by_geography <- function(year, fips = rndrng_prvdr_geo_cd, hcpcs_code = hcpcs_cd, hcpcs_desc, - hcpcs_drug = hcpcs_drug_ind, - place_of_srvc, + drug = hcpcs_drug_ind, + pos = place_of_srvc, tot_provs = tot_rndrng_prvdrs, tot_benes, tot_srvcs, tot_day = tot_bene_day_srvcs, - avg_charges = avg_sbmtd_chrg, + avg_charge = avg_sbmtd_chrg, avg_allowed = avg_mdcr_alowd_amt, avg_payment = avg_mdcr_pymt_amt, avg_std_pymt = avg_mdcr_stdzd_amt) |> dplyr::mutate(dplyr::across(dplyr::where(is.character), ~dplyr::na_if(., "")), - hcpcs_drug = yn_logical(hcpcs_drug), - place_of_srvc = pos_char(place_of_srvc), + drug = yn_logical(drug), + pos = pos_char(pos), dplyr::across(dplyr::contains("tot"), as.integer), dplyr::across(dplyr::contains("avg"), ~round(., digits = 2))) @@ -192,11 +191,11 @@ physician_by_geography <- function(year, #' Check the current years available for the Physician & Other Practitioners by Geography and Service API #' @return integer vector of years available #' @examples -#' physician_by_geography_years() +#' by_geography_years() #' @rdname years #' @autoglobal #' @export -physician_by_geography_years <- function() { +by_geography_years <- function() { cms_update("Medicare Physician & Other Practitioners - by Geography and Service", "years") |> as.integer() } diff --git a/R/physician_by_provider.R b/R/physician_by_provider.R index d7066b0d..5511bd91 100644 --- a/R/physician_by_provider.R +++ b/R/physician_by_provider.R @@ -1,16 +1,17 @@ #' Yearly Utilization Data on Medicare Part B Providers #' -#' @description `physician_by_provider()` allows you to access data such as +#' @description `by_provider()` allows you to access data such as #' services and procedures performed; charges submitted and payment received; #' and beneficiary demographic and health characteristics for providers treating #' Original Medicare (fee-for-service) Part B beneficiaries, aggregated by year. #' -#' @section Links: +#' ### Links: #' - [Medicare Physician & Other Practitioners: by Provider API](https://data.cms.gov/provider-summary-by-type-of-service/medicare-physician-other-practitioners/medicare-physician-other-practitioners-by-provider) #' -#' @section Update Frequency: **Annually* +#' *Update Frequency:* **Annually** +#' #' @param year integer (*required*); Year in `YYYY` format. Run helper function -#' `physician_by_provider_years()` to return a vector of the years +#' `by_provider_years()` to return a vector of the years #' currently available. #' @param npi National Provider Identifier for the rendering provider on the claim. #' @param first_name Individual provider's first name. @@ -22,7 +23,7 @@ #' @param city City where provider is located. #' @param state State where provider is located. #' @param fips Provider's state FIPS code. -#' @param zipcode Provider’s zip code. +#' @param zip Provider’s zip code. #' @param ruca Rural-Urban Commuting Area Code (RUCA); a Census tract-based #' classification scheme that utilizes the standard Bureau of Census #' Urbanized Area and Urban Cluster definitions in combination with work @@ -45,10 +46,6 @@ #' #' @return A [tibble][tibble::tibble-package] containing the search results. #' -#' @seealso [physician_by_provider_years()], [physician_by_service()], -#' [physician_by_geography()], [beneficiary_enrollment()], [cc_multiple()], -#' [cc_specific()] -#' #' @examplesIf interactive() #' physician_by_provider(year = 2020, #' npi = 1003000423) @@ -57,40 +54,32 @@ #' physician_by_provider_years() |> #' map(\(x) physician_by_provider(year = x, npi = 1043477615)) |> #' list_rbind() -#' @rdname provider-statistics #' @autoglobal #' @export -physician_by_provider <- function(year, - npi = NULL, - first_name = NULL, - last_name = NULL, - organization_name = NULL, - credential = NULL, - gender = NULL, - entype = NULL, - city = NULL, - state = NULL, - zipcode = NULL, - fips = NULL, - ruca = NULL, - country = NULL, - specialty = NULL, - par = NULL, - tidy = TRUE) { - - # if (!is.null(year)) { - # years <- physician_by_provider_years() - # cli::cli_abort(c( - # "{.var year} is required", - # "i" = "Years available are {.val years}", wrap = TRUE - # )) - # } +by_provider <- function(year, + npi = NULL, + first_name = NULL, + last_name = NULL, + organization_name = NULL, + credential = NULL, + gender = NULL, + entype = NULL, + city = NULL, + state = NULL, + zip = NULL, + fips = NULL, + ruca = NULL, + country = NULL, + specialty = NULL, + par = NULL, + tidy = TRUE) { if (!is.null(npi)) {npi_check(npi)} # match args + rlang::check_required(year) year <- as.character(year) - rlang::arg_match(year, values = as.character(physician_by_provider_years())) + year <- rlang::arg_match(year, values = as.character(by_provider_years())) # update distribution ids id <- cms_update(api = "Medicare Physician & Other Practitioners - by Provider", @@ -111,7 +100,7 @@ physician_by_provider <- function(year, "Rndrng_Prvdr_City", city, "Rndrng_Prvdr_State_Abrvtn", state, "Rndrng_Prvdr_State_FIPS", fips, - "Rndrng_Prvdr_Zip5", zipcode, + "Rndrng_Prvdr_Zip5", zip, "Rndrng_Prvdr_RUCA", ruca, "Rndrng_Prvdr_Cntry", country, "Rndrng_Prvdr_Type", specialty, @@ -147,7 +136,7 @@ physician_by_provider <- function(year, "city", city, "state", state, "fips", as.character(fips), - "zipcode", as.character(zipcode), + "zip", as.character(zip), "ruca", as.character(ruca), "country", country, "specialty", specialty, @@ -194,7 +183,7 @@ physician_by_provider <- function(year, city = rndrng_prvdr_city, state = rndrng_prvdr_state_abrvtn, fips = rndrng_prvdr_state_fips, - zipcode = rndrng_prvdr_zip5, + zip = rndrng_prvdr_zip5, ruca = rndrng_prvdr_ruca, # ruca_desc = rndrng_prvdr_ruca_desc, country = rndrng_prvdr_cntry, @@ -270,11 +259,11 @@ physician_by_provider <- function(year, #' Check the current years available for the Physician & Other Practitioners by Provider API #' @return integer vector of years available #' @examples -#' physician_by_provider_years() +#' by_provider_years() #' @autoglobal #' @export #' @rdname years -physician_by_provider_years <- function() { +by_provider_years <- function() { cms_update("Medicare Physician & Other Practitioners - by Provider", "years") |> as.integer() } diff --git a/R/physician_by_service.R b/R/physician_by_service.R index 2ce76354..c05c4556 100644 --- a/R/physician_by_service.R +++ b/R/physician_by_service.R @@ -28,32 +28,25 @@ #' because separate fee schedules apply depending on whether the place #' of service submitted on the claim is facility or non-facility. #' -#' @references -#' * [Medicare Physician & Other Practitioners: by Provider and Service API](https://data.cms.gov/provider-summary-by-type-of-service/medicare-physician-other-practitioners/medicare-physician-other-practitioners-by-provider-and-service) -#' @source Centers for Medicare & Medicaid Services -#' @note Update Frequency: **Annually** -#' @param year int (required); Year in YYYY format. Run helper function -#' `provider:::physician_by_service_years()` to return a vector of the years +#' ### Links +#' - [Medicare Physician & Other Practitioners: by Provider and Service API](https://data.cms.gov/provider-summary-by-type-of-service/medicare-physician-other-practitioners/medicare-physician-other-practitioners-by-provider-and-service) +#' +#' *Update Frequency:* **Annually** +#' +#' @param year integer (*required*); Year in `YYYY` format. Run helper function +#' `by_service_years()` to return a vector of the years #' currently available. -#' @param npi National Provider Identifier (NPI) for the rendering provider -#' on the claim. The provider NPI is the numeric identifier registered in -#' NPPES. -#' @param last_name Last name/Organization name of the provider. When the -#' provider is registered in NPPES as an individual (entity type code = `I`), -#' this is the provider’s last name. When the provider is registered as an -#' organization (entity type code = `O`), this is the organization name. -#' @param first_name An individual provider's (entity type code = `I`) first name. -#' An organization's (entity type code = `O`) will be blank. -#' @param credential An individual provider's (entity type code=’I’) credentials. An organization's will be blank. -#' @param gender An individual provider's gender. An organization's will be blank. -#' @param entype Type of entity reported in NPPES. An entity code of ‘I’ -#' identifies providers registered as individuals while an entity type -#' code of ‘O’ identifies providers registered as organizations. -#' @param city The city where the provider is located, as reported in NPPES. -#' @param state The state where the provider is located, as reported -#' in NPPES. -#' @param fips FIPS code for the rendering provider's state. -#' @param zipcode The provider’s zip code, as reported in NPPES. +#' @param npi National Provider Identifier for the rendering provider on the claim. +#' @param first_name Individual provider's first name. +#' @param last_name Individual provider's last name. +#' @param organization_name Organization name. +#' @param credential Individual provider's credentials. +#' @param gender Individual provider's gender. +#' @param entype Provider entity type. +#' @param city City where provider is located. +#' @param state State where provider is located. +#' @param fips Provider's state FIPS code. +#' @param zip Provider’s zip code. #' @param ruca Rural-Urban Commuting Area Code (RUCA); a Census tract-based #' classification scheme that utilizes the standard Bureau of Census #' Urbanized Area and Urban Cluster definitions in combination with work @@ -61,12 +54,9 @@ #' regarding their rural and urban status and relationships. The Referring #' Provider ZIP code was cross walked to the United States Department of #' Agriculture (USDA) 2010 Rural-Urban Commuting Area Codes. -#' @param country The country where the provider is located, as reported -#' in NPPES. -#' @param specialty Derived from the provider specialty code reported on the -#' claim. For providers that reported more than one specialty code on their -#' claims, this is the specialty code associated with the largest number -#' of services. +#' @param country Country where provider is located. +#' @param specialty Provider specialty code reported on the largest number of +#' claims submitted. #' @param par Identifies whether the provider participates in Medicare #' and/or accepts assignment of Medicare allowed amounts. The value will #' be `Y` for any provider that had at least one claim identifying the @@ -81,92 +71,50 @@ #' by the American Medical Association and Level II codes are created by #' CMS to identify products, supplies and services not covered by the CPT #' codes (such as ambulance services). -#' @param hcpcs_drug Identifies whether the HCPCS code for the specific service +#' @param drug Identifies whether the HCPCS code for the specific service #' furnished by the provider is a HCPCS listed on the Medicare Part B Drug #' Average Sales Price (ASP) File. Please visit the ASP drug pricing page #' for additional information. -#' @param place_of_srvc Identifies whether the place of service submitted on the claims -#' is a facility (value of `F`) or non-facility (value of `O`). Non-facility -#' is generally an office setting; however other entities are included -#' in non-facility. +#' @param pos Identifies whether the place of service submitted on the claims +#' is a facility (`F`) or non-facility (`O`). Non-facility is generally an +#' office setting; however other entities are included in non-facility. #' @param tidy Tidy output; default is `TRUE`. -#' @returns A [tibble][tibble::tibble-package] containing 29 columns: -#' \item{year}{year} -#' \item{npi}{year} -#' \item{entype}{Entity/Enumeration Type of the Provider} -#' \item{first_name}{year} -#' \item{middle_name}{year} -#' \item{last_name}{year} -#' \item{credential}{year} -#' \item{gender}{year} -#' \item{specialty}{year} -#' \item{street}{ the provider’s street address} -#' \item{city}{The city where the provider is located, as reported in NPPES.} -#' \item{state}{State Abbreviation of the Provider} -#' \item{fips}{State FIPS Code of the Provider} -#' \item{zipcode}{Zip Code of the Provider} -#' \item{ruca}{RUCA Code of the Provider} -#' \item{country}{Country Code of the Provider} -#' \item{par}{Medicare Participation Indicator} -#' \item{hcpcs_cd}{HCPCS Code} -#' \item{hcpcs_desc}{HCPCS Description} -#' \item{hcpcs_drug}{HCPCS Drug Indicator} -#' \item{pos}{Place of Service} -#' \item{tot_benes}{Number of Medicare Beneficiaries} -#' \item{tot_srvcs}{Number of Services} -#' \item{tot_day}{Number of Distinct Medicare Beneficiary/Per Day Services} -#' \item{avg_charge}{Average Submitted Charge Amount} -#' \item{avg_allowed}{Average Medicare Allowed Amount} -#' \item{avg_payment}{Average Medicare Payment Amount} -#' \item{avg_std_pymt}{Average Medicare Standardized Payment Amount} +#' +#' @returns A [tibble][tibble::tibble-package] containing the search results. +#' #' @examplesIf interactive() #' physician_by_service(npi = 1003000126) #' physician_by_service(year = 2019, last_name = "Enkeshafi") -#' c(1003026055, 1316405939, 1720392988) |> -#' purrr::map(physician_by_service, year = 2020) |> -#' purrr::list_rbind() -#' @rdname provider-statistics #' @autoglobal #' @export -physician_by_service <- function(year, - npi = NULL, - last_name = NULL, - first_name = NULL, - credential = NULL, - gender = NULL, - entype = NULL, - city = NULL, - state = NULL, - zipcode = NULL, - fips = NULL, - ruca = NULL, - country = NULL, - specialty = NULL, - par = NULL, - hcpcs_code = NULL, - hcpcs_drug = NULL, - place_of_srvc = NULL, - tidy = TRUE) { +by_service <- function(year, + npi = NULL, + last_name = NULL, + first_name = NULL, + organization_name = NULL, + credential = NULL, + gender = NULL, + entype = NULL, + city = NULL, + state = NULL, + zip = NULL, + fips = NULL, + ruca = NULL, + country = NULL, + specialty = NULL, + par = NULL, + hcpcs_code = NULL, + drug = NULL, + pos = NULL, + tidy = TRUE) { if (!is.null(npi)) {npi_check(npi)} - if (!is.null(place_of_srvc)) { - place_of_srvc <- dplyr::case_when( - place_of_srvc == "facility" ~ "F", - place_of_srvc == "Facility" ~ "F", - place_of_srvc == "F" ~ "F", - place_of_srvc == "f" ~ "F", - place_of_srvc == "office" ~ "O", - place_of_srvc == "Office" ~ "O", - place_of_srvc == "O" ~ "O", - place_of_srvc == "o" ~ "O", - .default = NULL) - } + if (!is.null(pos)) {pos <- pos_char(pos)} - # match args ---------------------------------------------------- rlang::check_required(year) year <- as.character(year) - rlang::arg_match(year, values = as.character(physician_by_service_years())) + rlang::arg_match(year, values = as.character(by_service_years())) # update distribution ids ------------------------------------------------- id <- cms_update(api = "Medicare Physician & Other Practitioners - by Provider and Service", check = "id") |> @@ -177,22 +125,23 @@ physician_by_service <- function(year, args <- tibble::tribble( ~x, ~y, "Rndrng_NPI", npi, - "Rndrng_Prvdr_Last_Org_Name", last_name, "Rndrng_Prvdr_First_Name", first_name, + "Rndrng_Prvdr_Last_Org_Name", last_name, + "Rndrng_Prvdr_Last_Org_Name", organization_name, "Rndrng_Prvdr_Crdntls", credential, "Rndrng_Prvdr_Gndr", gender, "Rndrng_Prvdr_Ent_Cd", entype, "Rndrng_Prvdr_City", city, "Rndrng_Prvdr_State_Abrvtn", state, "Rndrng_Prvdr_State_FIPS", fips, - "Rndrng_Prvdr_Zip5", zipcode, + "Rndrng_Prvdr_Zip5", zip, "Rndrng_Prvdr_RUCA", ruca, "Rndrng_Prvdr_Cntry", country, "Rndrng_Prvdr_Type", specialty, "Rndrng_Prvdr_Mdcr_Prtcptg_Ind", par, "HCPCS_Cd", hcpcs_code, - "HCPCS_Drug_Ind", hcpcs_drug, - "Place_Of_Srvc", place_of_srvc) + "HCPCS_Drug_Ind", drug, + "Place_Of_Srvc", pos) # map param_format and collapse ------------------------------------------- params_args <- purrr::map2(args$x, args$y, param_format) |> @@ -217,20 +166,21 @@ physician_by_service <- function(year, "npi", as.character(npi), "last_name", last_name, "first_name", first_name, + "organization_name", organization_name, "credential", credential, "gender", gender, "entype", entype, "city", city, "state", state, "fips", as.character(fips), - "zipcode", zipcode, + "zip", zip, "ruca", ruca, "country", country, "specialty", specialty, "par", par, "hcpcs_code", as.character(hcpcs_code), - "hcpcs_drug", as.character(hcpcs_drug), - "place_of_srvc", place_of_srvc) |> + "drug", as.character(drug), + "pos", pos) |> tidyr::unnest(cols = c(y)) cli_args <- purrr::map2(cli_args$x, @@ -250,7 +200,7 @@ physician_by_service <- function(year, # clean names ------------------------------------------------------------- if (tidy) { - results <- dplyr::rename_with(results, str_to_snakecase) |> + results <- janitor::clean_names(results) |> dplyr::mutate(year = as.integer(year), dplyr::across(c(tot_benes, tot_srvcs, @@ -275,25 +225,25 @@ physician_by_service <- function(year, city = rndrng_prvdr_city, state = rndrng_prvdr_state_abrvtn, fips = rndrng_prvdr_state_fips, - zipcode = rndrng_prvdr_zip5, + zip = rndrng_prvdr_zip5, ruca = rndrng_prvdr_ruca, #ruca_desc = rndrng_prvdr_ruca_desc, country = rndrng_prvdr_cntry, par = rndrng_prvdr_mdcr_prtcptg_ind, hcpcs_code = hcpcs_cd, hcpcs_desc, - hcpcs_drug = hcpcs_drug_ind, - place_of_srvc, + drug = hcpcs_drug_ind, + pos = place_of_srvc, tot_benes, tot_srvcs, tot_day = tot_bene_day_srvcs, - avg_charges = avg_sbmtd_chrg, + avg_charge = avg_sbmtd_chrg, avg_allowed = avg_mdcr_alowd_amt, avg_payment = avg_mdcr_pymt_amt, avg_std_pymt = avg_mdcr_stdzd_amt) |> dplyr::mutate(credential = clean_credentials(credential), entype = entype_char(entype), - place_of_srvc = pos_char(place_of_srvc), + pos = pos_char(pos), par = yn_logical(par)) } return(results) @@ -302,11 +252,11 @@ physician_by_service <- function(year, #' Check the current years available for the Physician & Other Practitioners by Provider and Service API #' @return integer vector of years available #' @examples -#' physician_by_service_years() +#' by_service_years() #' @rdname years #' @autoglobal #' @export -physician_by_service_years <- function() { +by_service_years <- function() { cms_update("Medicare Physician & Other Practitioners - by Provider and Service", "years") |> as.integer() } diff --git a/R/utils.R b/R/utils.R index e5bb36b1..9e02bd1c 100644 --- a/R/utils.R +++ b/R/utils.R @@ -236,20 +236,10 @@ yn_logical <- function(x) { #' @noRd entype_char <- function(x) { - ## TO DO Convert to case_match() - - # dplyr::case_match( - # x, - # c("I", "i", "Ind", "ind", "1") ~ "NPI-1", - # c("O", "o", "Org", "org", "2") ~ "NPI-2", - # .default = NULL - # ) - - dplyr::case_when( - x == "NPI-1" ~ "Individual", - x == "I" ~ "Individual", - x == "NPI-2" ~ "Organization", - x == "O" ~ "Organization" + dplyr::case_match(x, + c("NPI-1", "I") ~ "Individual", + c("NPI-2", "O") ~ "Organization", + .default = x ) } @@ -269,38 +259,23 @@ entype_arg <- function(x) { ) } -#' Convert Place of Service values ---------------------- +#' Convert Place of Service values #' @param x vector #' @autoglobal #' @noRd -pos_char <- function(x){ - - ## TO DO Convert to case_match() +pos_char <- function(x) { - # dplyr::case_match( - # x, - # c("I", "i", "Ind", "ind", "1") ~ "NPI-1", - # c("O", "o", "Org", "org", "2") ~ "NPI-2", - # .default = NULL - # ) - - dplyr::case_when( - x == "facility" ~ "F", - x == "Facility" ~ "F", - x == "F" ~ "F", - x == "f" ~ "F", - x == "office" ~ "O", - x == "Office" ~ "O", - x == "O" ~ "O", - x == "o" ~ "O", - .default = NULL) -} + dplyr::case_match(x, + c("facility", "Facility", "F", "f") ~ "F", + c("office", "Office", "O", "o") ~ "O", + .default = NULL) + } -#' display_long ------------------------------------------------------------ +#' display_long #' @param df data frame #' @autoglobal #' @noRd -display_long <- function(df){ +display_long <- function(df) { df |> dplyr::mutate(dplyr::across(dplyr::everything(), as.character)) |> diff --git a/man/by_geography.Rd b/man/by_geography.Rd new file mode 100644 index 00000000..74749174 --- /dev/null +++ b/man/by_geography.Rd @@ -0,0 +1,115 @@ +% Generated by roxygen2: do not edit by hand +% Please edit documentation in R/physician_by_geography.R +\name{by_geography} +\alias{by_geography} +\title{Search the Medicare Physician & Other Practitioners API +by \strong{Geography and Service}} +\usage{ +by_geography( + year, + level = NULL, + sublevel = NULL, + fips = NULL, + hcpcs_code = NULL, + hcpcs_desc = NULL, + drug = NULL, + pos = NULL, + tidy = TRUE +) +} +\arguments{ +\item{year}{int (required); Year in YYYY format. Run helper function +\code{by_geography_years()} to return a vector of the years +currently available.} + +\item{level}{Identifies the level of geography by which the data in the +row has been aggregated. A value of 'State' indicates the data in the +row is aggregated to a single state identified in the Rendering Provider +State column for a given HCPCS Code Level. A value of 'National' +indicates the data in the row is aggregated across all states for a +given HCPCS Code Level.} + +\item{sublevel}{The state name where the provider is located, as reported +in NPPES. The values include the 50 United States, District of Columbia, +U.S. territories, Armed Forces areas, Unknown and Foreign Country. Data +aggregated at the National level are identified by the word 'National'.} + +\item{fips}{FIPS code of the referring provider state. This variable is +blank when reported at the national level.} + +\item{hcpcs_code}{HCPCS code used to identify the specific medical service +furnished by the provider.} + +\item{hcpcs_desc}{Description of the HCPCS code for the specific medical +service furnished by the provider. HCPCS descriptions associated with +CPT codes are consumer friendly descriptions provided by the AMA. CPT +Consumer Friendly Descriptors are lay synonyms for CPT descriptors that +are intended to help healthcare consumers who are not medical +professionals understand clinical procedures on bills and patient +portals. CPT Consumer Friendly Descriptors should not be used for +clinical coding or documentation. All other descriptions are CMS Level +II descriptions provided in long form. Due to variable length +restrictions, the CMS Level II descriptions have been truncated to +256 bytes. As a result, the same HCPCS description can be associated +with more than one HCPCS code.} + +\item{drug}{Flag that identifies whether the HCPCS code for the specific +service furnished by the provider is a HCPCS listed on the Medicare Part +B Drug Average Sales Price (ASP) File.} + +\item{pos}{Identifies whether the place of service submitted on the claims +is a facility (\code{facility}) or non-facility (\code{office}). Non-facility +is generally an office setting; however other entities are included +in non-facility.} + +\item{tidy}{Tidy output; default is \code{TRUE}.} +} +\value{ +A \link[tibble:tibble-package]{tibble} containing the search results. +} +\description{ +Information on services and procedures provided to +Original Medicare (fee-for-service) Part B (Medical Insurance) +beneficiaries by physicians and other healthcare professionals; +aggregated by geography and service. +} +\details{ +The \strong{Geography and Service} dataset contains information on +utilization, payment (allowed amount and Medicare payment), and +submitted charges organized by HCPCS and place of service in the +national table and organized by provider state, HCPCS and place of +service in the state table. The national and state tables also include +a HCPCS drug indicator to identify whether the HCPCS product/service is +a drug as defined from the Medicare Part B Drug ASP list. +\subsection{Links}{ +\itemize{ +\item \href{https://data.cms.gov/provider-summary-by-type-of-service/medicare-physician-other-practitioners/medicare-physician-other-practitioners-by-geography-and-service}{Medicare Physician & Other Practitioners: by Geography and Service API} +} +} +} +\note{ +Update Frequency: \strong{Annually} +} +\examples{ +\dontshow{if (interactive()) (if (getRversion() >= "3.4") withAutoprint else force)(\{ # examplesIf} +physician_by_geography(hcpcs_code = "0002A", year = 2020) +service <- purrr::map_dfr(as.character(2013:2020), + ~physician_by_service(npi = 1003000126, year = .x)) + +procedures <- service |> + dplyr::distinct(hcpcs_cd) |> + tibble::deframe() + +arg_cross <- purrr::cross_df(list( + x = as.character(2013:2020), + y = procedures)) + +# National Level +purrr::map2_dfr(arg_cross$x, arg_cross$y, +~physician_by_geography(geo_level = "National", year = .x, hcpcs_code = .y)) + +# State Level +purrr::map2_dfr(arg_cross$x, arg_cross$y, +~physician_by_geography(geo_level = "Georgia", year = .x, hcpcs_code = .y)) +\dontshow{\}) # examplesIf} +} diff --git a/man/by_provider.Rd b/man/by_provider.Rd new file mode 100644 index 00000000..d85369da --- /dev/null +++ b/man/by_provider.Rd @@ -0,0 +1,104 @@ +% Generated by roxygen2: do not edit by hand +% Please edit documentation in R/physician_by_provider.R +\name{by_provider} +\alias{by_provider} +\title{Yearly Utilization Data on Medicare Part B Providers} +\usage{ +by_provider( + year, + npi = NULL, + first_name = NULL, + last_name = NULL, + organization_name = NULL, + credential = NULL, + gender = NULL, + entype = NULL, + city = NULL, + state = NULL, + zip = NULL, + fips = NULL, + ruca = NULL, + country = NULL, + specialty = NULL, + par = NULL, + tidy = TRUE +) +} +\arguments{ +\item{year}{integer (\emph{required}); Year in \code{YYYY} format. Run helper function +\code{by_provider_years()} to return a vector of the years +currently available.} + +\item{npi}{National Provider Identifier for the rendering provider on the claim.} + +\item{first_name}{Individual provider's first name.} + +\item{last_name}{Individual provider's last name.} + +\item{organization_name}{Organization name.} + +\item{credential}{Individual provider's credentials.} + +\item{gender}{Individual provider's gender.} + +\item{entype}{Provider entity type.} + +\item{city}{City where provider is located.} + +\item{state}{State where provider is located.} + +\item{zip}{Provider’s zip code.} + +\item{fips}{Provider's state FIPS code.} + +\item{ruca}{Rural-Urban Commuting Area Code (RUCA); a Census tract-based +classification scheme that utilizes the standard Bureau of Census +Urbanized Area and Urban Cluster definitions in combination with work +commuting information to characterize all of the nation's Census tracts +regarding their rural and urban status and relationships. The Referring +Provider ZIP code was cross walked to the United States Department of +Agriculture (USDA) 2010 Rural-Urban Commuting Area Codes.} + +\item{country}{Country where provider is located.} + +\item{specialty}{Provider specialty code reported on the largest number of +claims submitted.} + +\item{par}{Identifies whether the provider participates in Medicare +and/or accepts assignment of Medicare allowed amounts. The value will +be \code{Y} for any provider that had at least one claim identifying the +provider as participating in Medicare or accepting assignment of +Medicare allowed amounts within HCPCS code and place of service. A +non-participating provider may elect to accept Medicare allowed amounts +for some services and not accept Medicare allowed amounts for other +services.} + +\item{tidy}{Tidy output; default is \code{TRUE}.} +} +\value{ +A \link[tibble:tibble-package]{tibble} containing the search results. +} +\description{ +\code{by_provider()} allows you to access data such as +services and procedures performed; charges submitted and payment received; +and beneficiary demographic and health characteristics for providers treating +Original Medicare (fee-for-service) Part B beneficiaries, aggregated by year. +\subsection{Links:}{ +\itemize{ +\item \href{https://data.cms.gov/provider-summary-by-type-of-service/medicare-physician-other-practitioners/medicare-physician-other-practitioners-by-provider}{Medicare Physician & Other Practitioners: by Provider API} +} + +\emph{Update Frequency:} \strong{Annually} +} +} +\examples{ +\dontshow{if (interactive()) (if (getRversion() >= "3.4") withAutoprint else force)(\{ # examplesIf} +physician_by_provider(year = 2020, + npi = 1003000423) + +# Use the years helper function to retrieve results for every year: +physician_by_provider_years() |> +map(\(x) physician_by_provider(year = x, npi = 1043477615)) |> +list_rbind() +\dontshow{\}) # examplesIf} +} diff --git a/man/by_service.Rd b/man/by_service.Rd new file mode 100644 index 00000000..f3ed2672 --- /dev/null +++ b/man/by_service.Rd @@ -0,0 +1,143 @@ +% Generated by roxygen2: do not edit by hand +% Please edit documentation in R/physician_by_service.R +\name{by_service} +\alias{by_service} +\title{Search the Medicare Physician & Other Practitioners API +by \strong{Provider and Service}} +\usage{ +by_service( + year, + npi = NULL, + last_name = NULL, + first_name = NULL, + organization_name = NULL, + credential = NULL, + gender = NULL, + entype = NULL, + city = NULL, + state = NULL, + zip = NULL, + fips = NULL, + ruca = NULL, + country = NULL, + specialty = NULL, + par = NULL, + hcpcs_code = NULL, + drug = NULL, + pos = NULL, + tidy = TRUE +) +} +\arguments{ +\item{year}{integer (\emph{required}); Year in \code{YYYY} format. Run helper function +\code{by_service_years()} to return a vector of the years +currently available.} + +\item{npi}{National Provider Identifier for the rendering provider on the claim.} + +\item{last_name}{Individual provider's last name.} + +\item{first_name}{Individual provider's first name.} + +\item{organization_name}{Organization name.} + +\item{credential}{Individual provider's credentials.} + +\item{gender}{Individual provider's gender.} + +\item{entype}{Provider entity type.} + +\item{city}{City where provider is located.} + +\item{state}{State where provider is located.} + +\item{zip}{Provider’s zip code.} + +\item{fips}{Provider's state FIPS code.} + +\item{ruca}{Rural-Urban Commuting Area Code (RUCA); a Census tract-based +classification scheme that utilizes the standard Bureau of Census +Urbanized Area and Urban Cluster definitions in combination with work +commuting information to characterize all of the nation's Census tracts +regarding their rural and urban status and relationships. The Referring +Provider ZIP code was cross walked to the United States Department of +Agriculture (USDA) 2010 Rural-Urban Commuting Area Codes.} + +\item{country}{Country where provider is located.} + +\item{specialty}{Provider specialty code reported on the largest number of +claims submitted.} + +\item{par}{Identifies whether the provider participates in Medicare +and/or accepts assignment of Medicare allowed amounts. The value will +be \code{Y} for any provider that had at least one claim identifying the +provider as participating in Medicare or accepting assignment of +Medicare allowed amounts within HCPCS code and place of service. A +non-participating provider may elect to accept Medicare allowed amounts +for some services and not accept Medicare allowed amounts for other +services.} + +\item{hcpcs_code}{HCPCS code used to identify the specific medical service +furnished by the provider. HCPCS codes include two levels. Level I codes +are the Current Procedural Terminology (CPT) codes that are maintained +by the American Medical Association and Level II codes are created by +CMS to identify products, supplies and services not covered by the CPT +codes (such as ambulance services).} + +\item{drug}{Identifies whether the HCPCS code for the specific service +furnished by the provider is a HCPCS listed on the Medicare Part B Drug +Average Sales Price (ASP) File. Please visit the ASP drug pricing page +for additional information.} + +\item{pos}{Identifies whether the place of service submitted on the claims +is a facility (\code{F}) or non-facility (\code{O}). Non-facility is generally an +office setting; however other entities are included in non-facility.} + +\item{tidy}{Tidy output; default is \code{TRUE}.} +} +\value{ +A \link[tibble:tibble-package]{tibble} containing the search results. +} +\description{ +Information on services and procedures provided to +Original Medicare (fee-for-service) Part B (Medical Insurance) +beneficiaries by physicians and other healthcare professionals; +aggregated by provider and service. +} +\details{ +The \strong{Provider and Service} dataset provides information on +services and procedures provided to Medicare (fee-for-service) Part B +beneficiaries by physicians and other healthcare professionals. + +The data is based on information gathered from CMS administrative claims +data for Part B beneficiaries available from the CMS Chronic Conditions +Data Warehouse. + +The spending and utilization data in the Physician and Other +Practitioners by Provider and Service Dataset are aggregated +to the following: +\enumerate{ +\item the NPI for the performing provider, +\item the Healthcare Common Procedure Coding System (HCPCS) code, and +\item the place of service (either facility or non-facility). +} + +There can be multiple records for a given NPI based on the number of +distinct HCPCS codes that were billed and where the services were +provided. Data have been aggregated based on the place of service +because separate fee schedules apply depending on whether the place +of service submitted on the claim is facility or non-facility. +\subsection{Links}{ +\itemize{ +\item \href{https://data.cms.gov/provider-summary-by-type-of-service/medicare-physician-other-practitioners/medicare-physician-other-practitioners-by-provider-and-service}{Medicare Physician & Other Practitioners: by Provider and Service API} +} + +\emph{Update Frequency:} \strong{Annually} +} +} +\examples{ +\dontshow{if (interactive()) (if (getRversion() >= "3.4") withAutoprint else force)(\{ # examplesIf} +physician_by_service(npi = 1003000126) +physician_by_service(year = 2019, last_name = "Enkeshafi") +\dontshow{\}) # examplesIf} +} diff --git a/man/hospitals.Rd b/man/hospitals.Rd index d8d8f20c..5422276d 100644 --- a/man/hospitals.Rd +++ b/man/hospitals.Rd @@ -57,7 +57,7 @@ type and address. \item \href{https://data.cms.gov/provider-characteristics/hospitals-and-other-facilities/hospital-enrollments}{Hospital Enrollments} } -Update Frequency: \strong{Monthly} +\emph{Update Frequency:} \strong{Monthly} } } \examples{ diff --git a/man/missing_information.Rd b/man/missing_information.Rd index 4e8515e4..9e5f760f 100644 --- a/man/missing_information.Rd +++ b/man/missing_information.Rd @@ -45,22 +45,23 @@ information) of potential exchange partners to facilitate this information excha } \examples{ -# A provider that appears in the search results of the Missing Information -# API has no Endpoints entered into the NPPES NPI Registry and vice versa. +# A provider that appears in the search results +# of the Missing Information API has no Endpoints +# entered into the NPPES NPI Registry and vice versa. ## Appears missing_information(name = "Clouse, John") ## No Endpoints in NPPES -nppes_npi(npi = 1144224569, - tidy = FALSE) |> - dplyr::select(endpoints) +nppes(npi = 1144224569, + tidy = FALSE) |> + dplyr::select(endpoints) ## Does Not Appear missing_information(npi = 1003000423) ## Has Endpoints in NPPES -nppes_npi(npi = 1003000423, tidy = FALSE) |> +nppes(npi = 1003000423, tidy = FALSE) |> dplyr::select(endpoints) |> tidyr::unnest(cols = c(endpoints)) |> janitor::clean_names() |> @@ -68,5 +69,5 @@ dplyr::select(dplyr::contains("endpoint")) } \seealso{ -\code{\link[=nppes_npi]{nppes_npi()}} +\code{\link[=nppes]{nppes()}} } diff --git a/man/nppes_npi.Rd b/man/nppes.Rd similarity index 68% rename from man/nppes_npi.Rd rename to man/nppes.Rd index 440fed00..90c0a80f 100644 --- a/man/nppes_npi.Rd +++ b/man/nppes.Rd @@ -1,13 +1,10 @@ % Generated by roxygen2: do not edit by hand -% Please edit documentation in R/nppes_npi.R -\name{nppes_npi} -\alias{nppes_npi} -\title{Search the NPPES National Provider Identifier Registry API} -\source{ -Centers for Medicare & Medicaid Services -} +% Please edit documentation in R/nppes.R +\name{nppes} +\alias{nppes} +\title{National Registry of All Health Care Providers} \usage{ -nppes_npi( +nppes( npi = NULL, entype = NULL, first_name = NULL, @@ -27,16 +24,14 @@ nppes_npi( \arguments{ \item{npi}{10-digit National Provider Identifier (NPI).} -\item{entype}{Choices are either \code{I} for an Individual provider (NPI-1 or -Type 1) or \code{O} for an Organizational provider (NPI-2 or Type 2.). When -not specified, both Type 1 and Type 2 NPIs will be returned. Entype -cannot be the only criteria entered.} +\item{entype}{Entity type. Choices are either \code{I} for an Individual provider +or \code{O} for an Organizational provider. Cannot be the only criteria entered.} -\item{first_name}{Individual provider's (NPI-1) first name. Trailing wildcard +\item{first_name}{Individual provider's first name. Trailing wildcard entries are permitted requiring at least two characters to be entered (e.g. \verb{jo*} ).} -\item{last_name}{Individual provider's (NPI-1) last name. Trailing wildcard +\item{last_name}{Individual provider's last name. Trailing wildcard entries are permitted requiring at least two characters to be entered (e.g. \verb{jo*} ).} @@ -87,30 +82,25 @@ the previous number; set in \code{limit}.} A \link[tibble:tibble-package]{tibble} containing the search results. } \description{ -\code{nppes_npi()} allows you to search the NPPES NPI -Registry's public API by many of the parameters defined in the -API's documentation. -} -\details{ -The NPPES NPI Registry Public Search is a free directory of all -active National Provider Identifier (NPI) records. Healthcare providers -acquire their unique 10-digit NPIs to identify themselves in a standard -way throughout their industry. After CMS supplies an NPI, they publish -the parts of the NPI record that have public relevance, including the -provider’s name, taxonomy and practice address. It enables you to search -for providers in the NPPES (National Plan and Provider Enumeration -System.) All information produced by the NPI Registry is provided in -accordance with the NPPES Data Dissemination Notice. There is no charge -to use the NPI Registry. +\code{nppes()} allows you to search the National Plan and Provider Enumeration +System (NPPES) NPI Registry's public API. Th Registry is a free directory of +all active National Provider Identifier (NPI) records. +\subsection{National Provider Identifier (NPI)}{ + +Healthcare providers acquire their unique 10-digit NPIs to identify +themselves in a standard way throughout their industry. Once CMS supplies +an NPI, they publish the parts of the NPI record that have public relevance, +including the provider’s name, taxonomy and practice address. \subsection{Links}{ \itemize{ \item \href{https://npiregistry.cms.hhs.gov/api-page}{NPPES NPI Registry API Documentation} \item \href{https://npiregistry.cms.hhs.gov/demo-api}{NPPES NPI Registry API Demo} } + +\emph{Update Frequency:} \strong{Weekly} } + } -\note{ -Update Frequency: \strong{Weekly} } \examples{ \dontshow{if (interactive()) (if (getRversion() >= "3.4") withAutoprint else force)(\{ # examplesIf} diff --git a/man/provider-statistics.Rd b/man/provider-statistics.Rd deleted file mode 100644 index ae54acab..00000000 --- a/man/provider-statistics.Rd +++ /dev/null @@ -1,327 +0,0 @@ -% Generated by roxygen2: do not edit by hand -% Please edit documentation in R/physician_by_geography.R, -% R/physician_by_provider.R, R/physician_by_service.R -\name{physician_by_geography} -\alias{physician_by_geography} -\alias{physician_by_provider} -\alias{physician_by_service} -\title{Search the Medicare Physician & Other Practitioners API -by \strong{Geography and Service}} -\source{ -Centers for Medicare & Medicaid Services - -Centers for Medicare & Medicaid Services -} -\usage{ -physician_by_geography( - year, - level = NULL, - sublevel = NULL, - fips = NULL, - hcpcs_code = NULL, - hcpcs_desc = NULL, - hcpcs_drug = NULL, - place_of_srvc = NULL, - tidy = TRUE -) - -physician_by_provider( - year, - npi = NULL, - first_name = NULL, - last_name = NULL, - organization_name = NULL, - credential = NULL, - gender = NULL, - entype = NULL, - city = NULL, - state = NULL, - zipcode = NULL, - fips = NULL, - ruca = NULL, - country = NULL, - specialty = NULL, - par = NULL, - tidy = TRUE -) - -physician_by_service( - year, - npi = NULL, - last_name = NULL, - first_name = NULL, - credential = NULL, - gender = NULL, - entype = NULL, - city = NULL, - state = NULL, - zipcode = NULL, - fips = NULL, - ruca = NULL, - country = NULL, - specialty = NULL, - par = NULL, - hcpcs_code = NULL, - hcpcs_drug = NULL, - place_of_srvc = NULL, - tidy = TRUE -) -} -\arguments{ -\item{year}{int (required); Year in YYYY format. Run helper function -\code{provider:::physician_by_service_years()} to return a vector of the years -currently available.} - -\item{level}{Identifies the level of geography by which the data in the -row has been aggregated. A value of 'State' indicates the data in the -row is aggregated to a single state identified in the Rendering Provider -State column for a given HCPCS Code Level. A value of 'National' -indicates the data in the row is aggregated across all states for a -given HCPCS Code Level.} - -\item{sublevel}{The state name where the provider is located, as reported -in NPPES. The values include the 50 United States, District of Columbia, -U.S. territories, Armed Forces areas, Unknown and Foreign Country. Data -aggregated at the National level are identified by the word 'National'.} - -\item{fips}{FIPS code for the rendering provider's state.} - -\item{hcpcs_code}{HCPCS code used to identify the specific medical service -furnished by the provider. HCPCS codes include two levels. Level I codes -are the Current Procedural Terminology (CPT) codes that are maintained -by the American Medical Association and Level II codes are created by -CMS to identify products, supplies and services not covered by the CPT -codes (such as ambulance services).} - -\item{hcpcs_desc}{Description of the HCPCS code for the specific medical -service furnished by the provider. HCPCS descriptions associated with -CPT codes are consumer friendly descriptions provided by the AMA. CPT -Consumer Friendly Descriptors are lay synonyms for CPT descriptors that -are intended to help healthcare consumers who are not medical -professionals understand clinical procedures on bills and patient -portals. CPT Consumer Friendly Descriptors should not be used for -clinical coding or documentation. All other descriptions are CMS Level -II descriptions provided in long form. Due to variable length -restrictions, the CMS Level II descriptions have been truncated to -256 bytes. As a result, the same HCPCS description can be associated -with more than one HCPCS code.} - -\item{hcpcs_drug}{Identifies whether the HCPCS code for the specific service -furnished by the provider is a HCPCS listed on the Medicare Part B Drug -Average Sales Price (ASP) File. Please visit the ASP drug pricing page -for additional information.} - -\item{place_of_srvc}{Identifies whether the place of service submitted on the claims -is a facility (value of \code{F}) or non-facility (value of \code{O}). Non-facility -is generally an office setting; however other entities are included -in non-facility.} - -\item{tidy}{Tidy output; default is \code{TRUE}.} - -\item{npi}{National Provider Identifier (NPI) for the rendering provider -on the claim. The provider NPI is the numeric identifier registered in -NPPES.} - -\item{first_name}{An individual provider's (entity type code = \code{I}) first name. -An organization's (entity type code = \code{O}) will be blank.} - -\item{last_name}{Last name/Organization name of the provider. When the -provider is registered in NPPES as an individual (entity type code = \code{I}), -this is the provider’s last name. When the provider is registered as an -organization (entity type code = \code{O}), this is the organization name.} - -\item{organization_name}{Organization name.} - -\item{credential}{An individual provider's (entity type code=’I’) credentials. An organization's will be blank.} - -\item{gender}{An individual provider's gender. An organization's will be blank.} - -\item{entype}{Type of entity reported in NPPES. An entity code of ‘I’ -identifies providers registered as individuals while an entity type -code of ‘O’ identifies providers registered as organizations.} - -\item{city}{The city where the provider is located, as reported in NPPES.} - -\item{state}{The state where the provider is located, as reported -in NPPES.} - -\item{zipcode}{The provider’s zip code, as reported in NPPES.} - -\item{ruca}{Rural-Urban Commuting Area Code (RUCA); a Census tract-based -classification scheme that utilizes the standard Bureau of Census -Urbanized Area and Urban Cluster definitions in combination with work -commuting information to characterize all of the nation's Census tracts -regarding their rural and urban status and relationships. The Referring -Provider ZIP code was cross walked to the United States Department of -Agriculture (USDA) 2010 Rural-Urban Commuting Area Codes.} - -\item{country}{The country where the provider is located, as reported -in NPPES.} - -\item{specialty}{Derived from the provider specialty code reported on the -claim. For providers that reported more than one specialty code on their -claims, this is the specialty code associated with the largest number -of services.} - -\item{par}{Identifies whether the provider participates in Medicare -and/or accepts assignment of Medicare allowed amounts. The value will -be \code{Y} for any provider that had at least one claim identifying the -provider as participating in Medicare or accepting assignment of -Medicare allowed amounts within HCPCS code and place of service. A -non-participating provider may elect to accept Medicare allowed amounts -for some services and not accept Medicare allowed amounts for other -services.} -} -\value{ -A \link[tibble:tibble-package]{tibble} containing the search results. - -A \link[tibble:tibble-package]{tibble} containing the search results. - -A \link[tibble:tibble-package]{tibble} containing 29 columns: -\item{year}{year} -\item{npi}{year} -\item{entype}{Entity/Enumeration Type of the Provider} -\item{first_name}{year} -\item{middle_name}{year} -\item{last_name}{year} -\item{credential}{year} -\item{gender}{year} -\item{specialty}{year} -\item{street}{ the provider’s street address} -\item{city}{The city where the provider is located, as reported in NPPES.} -\item{state}{State Abbreviation of the Provider} -\item{fips}{State FIPS Code of the Provider} -\item{zipcode}{Zip Code of the Provider} -\item{ruca}{RUCA Code of the Provider} -\item{country}{Country Code of the Provider} -\item{par}{Medicare Participation Indicator} -\item{hcpcs_cd}{HCPCS Code} -\item{hcpcs_desc}{HCPCS Description} -\item{hcpcs_drug}{HCPCS Drug Indicator} -\item{pos}{Place of Service} -\item{tot_benes}{Number of Medicare Beneficiaries} -\item{tot_srvcs}{Number of Services} -\item{tot_day}{Number of Distinct Medicare Beneficiary/Per Day Services} -\item{avg_charge}{Average Submitted Charge Amount} -\item{avg_allowed}{Average Medicare Allowed Amount} -\item{avg_payment}{Average Medicare Payment Amount} -\item{avg_std_pymt}{Average Medicare Standardized Payment Amount} -} -\description{ -Information on services and procedures provided to -Original Medicare (fee-for-service) Part B (Medical Insurance) -beneficiaries by physicians and other healthcare professionals; -aggregated by geography and service. - -\code{physician_by_provider()} allows you to access data such as -services and procedures performed; charges submitted and payment received; -and beneficiary demographic and health characteristics for providers treating -Original Medicare (fee-for-service) Part B beneficiaries, aggregated by year. - -Information on services and procedures provided to -Original Medicare (fee-for-service) Part B (Medical Insurance) -beneficiaries by physicians and other healthcare professionals; -aggregated by provider and service. -} -\details{ -The \strong{Geography and Service} dataset contains information on -utilization, payment (allowed amount and Medicare payment), and -submitted charges organized by HCPCS and place of service in the -national table and organized by provider state, HCPCS and place of -service in the state table. The national and state tables also include -a HCPCS drug indicator to identify whether the HCPCS product/service is -a drug as defined from the Medicare Part B Drug ASP list. -\subsection{Links}{ -\itemize{ -\item \href{https://data.cms.gov/provider-summary-by-type-of-service/medicare-physician-other-practitioners/medicare-physician-other-practitioners-by-geography-and-service}{Medicare Physician & Other Practitioners: by Geography and Service API} -} -} - -The \strong{Provider and Service} dataset provides information on -services and procedures provided to Medicare (fee-for-service) Part B -beneficiaries by physicians and other healthcare professionals. - -The data is based on information gathered from CMS administrative claims -data for Part B beneficiaries available from the CMS Chronic Conditions -Data Warehouse. - -The spending and utilization data in the Physician and Other -Practitioners by Provider and Service Dataset are aggregated -to the following: -\enumerate{ -\item the NPI for the performing provider, -\item the Healthcare Common Procedure Coding System (HCPCS) code, and -\item the place of service (either facility or non-facility). -} - -There can be multiple records for a given NPI based on the number of -distinct HCPCS codes that were billed and where the services were -provided. Data have been aggregated based on the place of service -because separate fee schedules apply depending on whether the place -of service submitted on the claim is facility or non-facility. -} -\note{ -Update Frequency: \strong{Annually} - -Update Frequency: \strong{Annually} -} -\section{Links}{ - -\itemize{ -\item \href{https://data.cms.gov/provider-summary-by-type-of-service/medicare-physician-other-practitioners/medicare-physician-other-practitioners-by-provider}{Medicare Physician & Other Practitioners: by Provider API} -} -} - -\section{Update Frequency}{ - *\emph{Annually} -} - -\examples{ -\dontshow{if (interactive()) (if (getRversion() >= "3.4") withAutoprint else force)(\{ # examplesIf} -physician_by_geography(hcpcs_code = "0002A", year = 2020) -service <- purrr::map_dfr(as.character(2013:2020), - ~physician_by_service(npi = 1003000126, year = .x)) - -procedures <- service |> - dplyr::distinct(hcpcs_cd) |> - tibble::deframe() - -arg_cross <- purrr::cross_df(list( - x = as.character(2013:2020), - y = procedures)) - -# National Level -purrr::map2_dfr(arg_cross$x, arg_cross$y, -~physician_by_geography(geo_level = "National", year = .x, hcpcs_code = .y)) - -# State Level -purrr::map2_dfr(arg_cross$x, arg_cross$y, -~physician_by_geography(geo_level = "Georgia", year = .x, hcpcs_code = .y)) -\dontshow{\}) # examplesIf} -\dontshow{if (interactive()) (if (getRversion() >= "3.4") withAutoprint else force)(\{ # examplesIf} -physician_by_provider(year = 2020, - npi = 1003000423) - -# Use the years helper function to retrieve results for every year: -physician_by_provider_years() |> -map(\(x) physician_by_provider(year = x, npi = 1043477615)) |> -list_rbind() -\dontshow{\}) # examplesIf} -\dontshow{if (interactive()) (if (getRversion() >= "3.4") withAutoprint else force)(\{ # examplesIf} -physician_by_service(npi = 1003000126) -physician_by_service(year = 2019, last_name = "Enkeshafi") -c(1003026055, 1316405939, 1720392988) |> - purrr::map(physician_by_service, year = 2020) |> - purrr::list_rbind() -\dontshow{\}) # examplesIf} -} -\references{ -\itemize{ -\item \href{https://data.cms.gov/provider-summary-by-type-of-service/medicare-physician-other-practitioners/medicare-physician-other-practitioners-by-provider-and-service}{Medicare Physician & Other Practitioners: by Provider and Service API} -} -} -\seealso{ -\code{\link[=physician_by_provider_years]{physician_by_provider_years()}}, \code{\link[=physician_by_service]{physician_by_service()}}, -\code{\link[=physician_by_geography]{physician_by_geography()}}, \code{\link[=beneficiary_enrollment]{beneficiary_enrollment()}}, \code{\link[=cc_multiple]{cc_multiple()}}, -\code{\link[=cc_specific]{cc_specific()}} -} diff --git a/man/years.Rd b/man/years.Rd index 2018c10e..65b081cf 100644 --- a/man/years.Rd +++ b/man/years.Rd @@ -6,9 +6,9 @@ \alias{cc_multiple_years} \alias{cc_specific_years} \alias{open_payments_years} -\alias{physician_by_geography_years} -\alias{physician_by_provider_years} -\alias{physician_by_service_years} +\alias{by_geography_years} +\alias{by_provider_years} +\alias{by_service_years} \alias{quality_payment_years} \title{Check the current years available for the Multiple Chronic Conditions API} \usage{ @@ -18,11 +18,11 @@ cc_specific_years() open_payments_years() -physician_by_geography_years() +by_geography_years() -physician_by_provider_years() +by_provider_years() -physician_by_service_years() +by_service_years() quality_payment_years() } @@ -60,8 +60,8 @@ Check the current years available for the Quality Payments API cc_multiple_years() cc_specific_years() open_payments_years() -physician_by_geography_years() -physician_by_provider_years() -physician_by_service_years() +by_geography_years() +by_provider_years() +by_service_years() quality_payment_years() } diff --git a/vignettes/articles/physician-by-provider.Rmd b/vignettes/articles/physician-by-provider.Rmd index 45d6eec4..65887a15 100644 --- a/vignettes/articles/physician-by-provider.Rmd +++ b/vignettes/articles/physician-by-provider.Rmd @@ -15,35 +15,73 @@ knitr::opts_chunk$set( out.width = "100%", fig.path = "man/figures/README-" ) +library(printr) ``` -```{r setup} +```{r message=FALSE, warning=FALSE} library(provider) +library(tidyverse) ``` - > The **Provider Utilization and Payment Data Physician and Other Practitioners Dataset** provides information on services and procedures provided to Original Medicare (fee-for-service) Part B (Medical Insurance) beneficiaries by physicians and other healthcare professionals. The **Provider** data subset provides information on use, payments, submitted charges and beneficiary demographic and health characteristics organized by NPI. +### Examples + +```{r} +by_provider_years() |> + map(\(x) by_provider(year = x, npi = 1023076643)) |> + list_rbind() |> + unnest_wider(conditions) |> + select(year, + first_name, + last_name, + credential, + city, + state, + ruca, + hcc_risk_avg, + contains("tot_")) +``` -The **Provider** data subset provides information on use, payments, submitted charges and beneficiary demographic and health characteristics organized by National Provider Identifier (NPI). This dataset is based on information gathered from CMS administrative claims data for Original Medicare Part B beneficiaries available from the CMS Chronic Conditions Data Warehouse. -### Examples ```{r} -physician_by_provider(year = 2021, - entype = "I", - city = "Hershey", - state = "PA", - fips = 42, - ruca = 1, - gender = "F", - credential = "MD", - specialty = "Anesthesiology") +by_service_years() |> + map(\(x) by_service(year = x, npi = 1023076643)) |> + list_rbind() |> + select(year, + city, + state, + ruca, + hcpcs_code, + hcpcs_desc, + pos, + tot_benes, + tot_srvcs, + avg_charge, + avg_allowed, + avg_payment) ``` -

+```{r} +srvc <- by_service_years() |> + map(\(x) by_service(year = x, npi = 1023076643)) |> + list_rbind() |> + select(year, hcpcs = hcpcs_code, pos) +srvc +# year <- as.list(srvc$year) +# hcpcs_code <- as.list(srvc$hcpcs) +# pos <- as.list(srvc$pos) +# +# l <- list(year = srvc$year, hcpcs_code = srvc$hcpcs, pos = srvc$pos) +# +# pmap(l, by_geography(year, hcpcs_code, pos, level = "National")) +``` +```{r} +by_geography(year = 2013, hcpcs_code = "99217", pos = "F") +``` ### Data Dictionary diff --git a/vignettes/provider.Rmd b/vignettes/provider.Rmd index d5cea251..9ee8e7aa 100644 --- a/vignettes/provider.Rmd +++ b/vignettes/provider.Rmd @@ -113,7 +113,6 @@ The following return yearly stats useful for comparison against data returned fr ### Auxiliary * `order_refer()`: Is a provider eligible to order and refer? - * `endpoints_missing()`: Is a provider missing Endpoints in the NPPES NPI Registry? * `pending()`: Has a provider's Medicare application been processed? * `taxonomy()`: Is a provider's specialty eligible to enroll in Medicare? * `qpp_stats()`: Yearly QPP/MIPS performance data.