GithubHelp home page GithubHelp logo

newrelic / newrelic-cli Goto Github PK

View Code? Open in Web Editor NEW
125.0 16.0 67.0 7.12 MB

The New Relic Command Line Interface

Home Page: https://developer.newrelic.com/explore-docs/newrelic-cli

License: Apache License 2.0

Makefile 2.05% Go 96.07% Dockerfile 0.01% Shell 1.53% Batchfile 0.04% PowerShell 0.22% Java 0.07%
developer-toolkit newrelic golang developer-tools cli go

newrelic-cli's Introduction

Community Project header

newrelic-cli

Testing Go Report Card GoDoc License CLA assistant Release Homebrew

Docker Stars Docker Pulls Docker Size Docker Version

The New Relic CLI is an officially supported command line interface for New Relic, released as part of the Developer Toolkit.

Overview

The New Relic CLI is a project to consolidate some of the tools that New Relic offers for managing resources. Current scope is limited while the framework is being developed, but the tool as-is does perform a subset of tasks.

  • Entity Search: Search for entities across all your New Relic accounts
  • Entity Tagging: Manage tags across all of your entities
  • Deployment Markers: Easily record an APM Application deployment within New Relic.

Getting Started

For a quick guide on getting started with the New Relic CLI, see our Getting Started page.

New Relic CLI Documentation

The latest New Relic CLI documentation is available in the repository's docs directory.

Installation & Upgrades

Installation options are available for various platforms. If you're running an older version of the CLI you can use these commands to update to the latest version.

MacOS

Automated install

curl -Ls https://download.newrelic.com/install/newrelic-cli/scripts/install.sh | bash

Homebrew

Install the New Relic CLI on MacOS via homebrew. With homebrew installed, run:

brew install newrelic-cli

Windows

Installation is supported on 64-bit Windows.

Automated install

[Net.ServicePointManager]::SecurityProtocol = 'tls12, tls'; (New-Object System.Net.WebClient).DownloadFile("https://download.newrelic.com/install/newrelic-cli/scripts/install.ps1", "$env:TEMP\install.ps1"); & $env:TEMP\install.ps1

Scoop

scoop bucket add newrelic-cli https://github.com/newrelic/newrelic-cli.git
scoop install newrelic-cli

Chocolatey

choco install newrelic-cli

Standalone installer

A standalone MSI installer is available on the New Relic download site. You can download the installer for the latest version here.

Powershell

Silent installation of the latest version of the CLI can be achieved via the follwing Powershell command:

(New-Object System.Net.WebClient).DownloadFile("https://github.com/newrelic/newrelic-cli/releases/latest/download/NewRelicCLIInstaller.msi", "$env:TEMP\NewRelicCLIInstaller.msi"); `
msiexec.exe /qn /i "$env:TEMP\NewRelicCLIInstaller.msi" | Out-Null; `

Linux

Automated install

curl -Ls https://download.newrelic.com/install/newrelic-cli/scripts/install.sh | bash

Snapcraft

Linux binaries can be installed via Snapcraft. With the snapd daemon installed, run:

sudo snap install newrelic-cli

Pre-built binaries

Pre-built binaries are available for all of the above platforms. You can download the latest releases here. The binaries and their checksums are signed and can be verified against the Developer Toolkit team's public PGP key.

Verify that the fingerprint for the downloaded key matches the following:

gpg --fingerprint [email protected]

5961 D131 BB2C 5C6B 42B1  4D0F 92AD A76A 30A3 F1FD

When verifying pre-built binaries and checksums, use the long format (the short format is not secure). For example:

gpg --keyid-format long --verify checksums.txt.sig checksums.txt

Docker

There is an official docker image that can be utilized for running commands as well.

Example Usage

Querying an APM application (using the Docker image)

# Pull the latest container
$ docker pull newrelic/cli

# Run the container interactively, remove it once the command exists
# Also must pass $NEW_RELIC_API_KEY to the container
$ docker run -it --rm \
    -e NEW_RELIC_API_KEY \
    newrelic/cli \
    apm application get --name WebPortal --accountId 2508259

[
  {
    "AccountID": 2508259,
    "ApplicationID": 204261368,
    "Domain": "APM",
    "EntityType": "APM_APPLICATION_ENTITY",
    "GUID": "MjUwODI1OXxBUE18QVBQTElDQVRJT058MjA0MjYxMzY4",
    "Name": "WebPortal",
    "Permalink": "https://one.newrelic.com/redirect/entity/MjUwODI1OXxBUE18QVBQTElDQVRJT058MjA0MjYxMzY4",
    "Reporting": true,
    "Type": "APPLICATION"
  }
]

See the Getting Started guide for a more in-depth introduction to the capabilities of the New Relic CLI.

Getting Help

In order to get help about what commands are available, the trusty --help flag is here to assist. Alternatively, using just the help subcommand also works.

newrelic --help
newrelic help

Help is also available for the nested sub-commands. For example, the with the following command, you can retrieve help for the apm sub-command.

newrelic apm --help
newrelic help apm

Using the CLI in this way, users are able to inspect what commands are available, with some instruction on their usage.

Patterns

Throughout the help, you may notice common patterns. The term describe is used to perform list or get operations, while the create and delete terms are used to construct or destroy an item, respectively.

Development

Requirements

  • Go 1.19+
  • GNU Make
  • git

Building

The newrelic command will be built in bin/ARCH/newrelic, where ARCH is either linux, darwin, or windows, depending on your build environment. You can run it directly from there or install it by moving it to a directory in your PATH.

# Default target is 'build'
$ make

# Explicitly run build
$ make build

# Locally test the CI build scripts
# make build-ci

Testing

Before contributing, all linting and tests must pass. Tests can be run directly via:

# Tests and Linting
$ make test

# Only unit tests
$ make test-unit

# Only integration tests
$ make test-integration

Working with recipes

Core recipe library

A core library of installation recipes is included with the CLI for use within the install command. Recipe files are syndicated from open-install-library and embedded in the CLI binary at release time. To fetch the latest recipe library while developing, the following make target can be used:

make recipes

Recipe files are stored in internal/install/recipes/files. Once files have been fetched, they will be included in future CLI builds. If a particular version of the recipe library is desired, the archive download URL can be passed to the make target via the RECIPES_ARCHIVE_URL option:

make recipes RECIPES_ARCHIVE_URL=https://github.com/newrelic/open-install-library/releases/download/v0.50.0/recipes.zip

To clean recipe files, use the recipes-clean target:

make recipes-clean

Custom recipe files

A path can also be passed to the --localRecipes flag when running the install command. This will bypass the methods described above and load files from the designated path.

Experimenting (internal New Relic usage only)

Using A/B tests, New Relic developers have the ability to gradually roll out new features.

Define an experiment

With access to Split.io, internal New Relic developers can create new A/B tests. Upon creating one, reference the exact name of the experiment in internal/split/constants.go. Make sure this is the exact name of the experiment in Split.io.

Retrieve treatments

You can retrieve the status of the treatment by using the SplitService.

// Retrieve a single treatment given an experiment (split)
treatment := split.SplitService.Get(split.VirtuosoCLITest)

if treatment == "on" {
  // insert code here to show on treatment
} else if treatment == "off" {
  // insert code here to show off treatment
} else {
  // insert your control treatment code here
}

// Retrieve multiple treatments given a list of experiments (splits)
splits := []string{split.VirtuosoCLITest, split.VirtuosoCliTest2}
treatments := split.SplitService.GetAll(splits)
for split, treatment := range treatments {
    fmt.Printf("Treatment for feature %s is %s\n", split, treatment)
    // Evaluate treatments
}

Commit Messages

Using the following format for commit messages allows for auto-generation of the CHANGELOG:

Format:

<type>(<scope>): <subject>

Type Description Change log?
chore Maintenance type work No
docs Documentation Updates Yes
feat New Features Yes
fix Bug Fixes Yes
refactor Code Refactoring No

Scope

This refers to what part of the code is the focus of the work. For example:

General:

  • build - Work related to the build system (linting, makefiles, CI/CD, etc)
  • release - Work related to cutting a new release

Package Specific:

  • newrelic - Work related to the New Relic package
  • http - Work related to the internal/http package
  • alerts - Work related to the pkg/alerts package

Generating CLI Documentation

Note: This requires the repo to be in your GOPATH (godoc issue)

$ make docs

Community Support

New Relic hosts and moderates an online forum where you can interact with New Relic employees as well as other customers to get help and share best practices.

  • Roadmap - As part of the Developer Toolkit, the roadmap for this project follows the same RFC process
  • Issues or Enhancement Requests - Issues and enhancement requests can be submitted in the Issues tab of this repository. Please search for and review the existing open issues before submitting a new issue.
  • Contributors Guide - Contributions are welcome (and if you submit a Enhancement Request, expect to be invited to contribute it yourself 😁).
  • Community discussion board - Like all official New Relic open source projects, there's a related Community topic in the New Relic Explorers Hub.

Please do not report issues with the CLI to New Relic Global Technical Support. Instead, visit the Explorers Hub for troubleshooting and best-practices.

Issues / Enhancement Requests

Issues and enhancement requests can be submitted in the Issues tab of this repository. Please search for and review the existing open issues before submitting a new issue.

Contributing

Contributions are welcome (and if you submit a Enhancement Request, expect to be invited to contribute it yourself 😁). Please review our Contributors Guide.

Keep in mind that when you submit your pull request, you'll need to sign the CLA via the click-through using CLA-Assistant. If you'd like to execute our corporate CLA, or if you have any questions, please drop us an email at [email protected].

Other Resources

There are a handful of other useful tools that this does not replace. Here are some useful links to other tools that you might be interested in using at this time.

  • NR1 CLI: Command line interface for managing development workflows for custom Nerdpacks on New Relic One.
  • New Relic Lambda CLI: A CLI to install the New Relic AWS Lambda integration and layers.
  • New Relic Diagnostics: A utility that automatically detects common problems with New Relic agents.

Open Source License

This project is distributed under the Apache 2 license.

newrelic-cli's People

Contributors

abrunner94 avatar amolero-nr avatar arenjae avatar chenrui333 avatar ctrombley avatar daffinito avatar devfreddy avatar glenofoghlu avatar jbeveland27 avatar jifeingo avatar julien4218 avatar kidk avatar mbazhlekova avatar mbruzina avatar michaelkro avatar natecanfield822 avatar noahmmcgivern avatar nr-developer-toolkit avatar nrhzhao avatar nsspkrishna avatar nunopi avatar olsonso avatar paologallinaharbur avatar pnvnd avatar pranav-new-relic avatar renovate-bot avatar renovate[bot] avatar rthorn-nr avatar sanderblue avatar zlesnr avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

newrelic-cli's Issues

Manual/automated testing for 2-way config/profiles compatibility with NR1 CLI

Objective

To ensure confidence in terms of compatibility with the configuration and credential files from the nr1 cli.

Acceptance Criteria

  • A known good example of all configuration files is available for use in testing.
  • Tests for each configuration file are present and the functionality of the config/profile loader works as expected.

Support -v and -vv flags for log level

Feature Description

The ability to increase verbosity with incremental -v flags seems potentially useful.

Describe Alternatives

Currently the logLevel configuration item is the way to enable more verbose logging.

Additional context

-vvv is a somewhat common pattern for CLI tools to use for increasing verbosity without the user needing to know the exact name of the log level and its "correct" letter casing.

Support composible topics

The plugin manifest model should be evolved to support composible topics, and should not assume that a plugin is 1:1 with a topic or secondary subcommand. For example: given a plugin A that defines commands B and C, a plugin X that defines commands Y and Z, and topics/secondary commands M and N, the manifest model should allow the composition of M->B, M->X, N->C, and N->Y.

Add configuration validation

The CLI is not currently validating configuration set commands.

AC:

  • Don't allow config values to be set that are not defined in the config struct
  • (Optional) Only allow NOT_ASKED, DISALLOW, and ALLOW for the sendUsageData key
  • (Optional) Only allow existing profile names for the profileName key
  • (Optional) Only allow valid log level strings for the logLevel key

Create a dockerfile

AC:

  • Create a dockerfile that allows the use of CLI commands.
  • It should also build an image that can be used for the above
  • Create a make target to create the docker image

Implement deployment marker retrieval

Objective

Support deployment marker retrieval via the CLI.

Acceptance Criteria

  • Add a deployments subcommand for listing an application's deployment markers by app ID
  • Provide help and example command invocation
  • CLI error code should match success/failure of the operation
  • Results should be returned in JSON format
  • AWS CLI uses "describe" as a verb, we can choose to use this as inspiration or stick with "get", "list", or something similar.

Notes

Potential command structure:
newrelic apm describe-deployments --applicationId <appID>

Config code refactoring and integration tests

Objective

The configuration command and associated code have acceptance tests that perform the read/write actions and assess the correctness.

Acceptance Criteria

  • Acceptance tests available, similar to what has been done for profiles.

Environment variables should override profiles

Objective

Be able to run the CLI without any configured profile, with Environment variables set.

Acceptance Criteria

  • Command executes with only API key set (default to US region)
  • Command executes with API key and Region set
  • Command executes with Env var for profile name set (todo: name this var)

Blocked by #35

Implement entity tag retrieval

Objective

Support Entity Tag retrieval via the CLI.

Acceptance Criteria

Notes

  • Entity tag data is available via the graphql paths actor.entities.tag and actor.entity.tags respectively.
  • AWS CLI uses "describe" as a verb, we can choose to use this as inspiration or stick with "get", "list", or something similar.

Potential command structure:
newrelic entities describe-tags --guid <guid1> --guid <guid2>

Refactor project structure

A couple different project structure conventions are being used by the packages in the CLI.

AC:

  • Move packages from the pkg directory into the internal directory
  • Remove the pkg directory
  • Move the cmd/root.go file into cmd/newrelic folder

Fix errorValue race condition

Description

Currently several portions of the code share an errorValue object for storing the error. We should refactor away from this and fix the underlying issue to ensure that each portion of the code.

Refactor config code for testability

AC:

  • Refactor the config code for testability
  • Add integration tests for setting various config values, modeled after the tests in profiles_integration_test.go

Powershell installation & associated docs

Objective

We'd like to ensure there is enough documentation for windows users to get started with the tool.

Acceptance Criteria

  • Installation docs for windows users
  • Powershell completion docs for windows users
  • Any known caveats are documented for the user

Remove application IDs from non-application entities

Objective

When an entity is returned in a query that is not an application, we would like to avoid having the application ID included.

Acceptance Criteria

  • Application entity results include their application ID
  • non-Application entity results do not include an application ID

Assumptions we want to be true but aren't quite

Bugs:

  • config set no longer works when there is no config file
  • apm create-deployment requires that you know the application id but we provide no way to learn an application id.
  • can't edit profiles (adding another API key for instance). need to delete and recreate
  • config get does not validate key names
  • config delete does not display a success message
  • config delete on a default profile does not un-set the default profile

Features:

  • Shell completion
  • bash/zsh/shell completion
  • version should also be a command, not just a flag.
  • add -v, -vv, -vvv for log level
  • Run "newrelic config get --key KEY" for more info, but doing so provides no extra information

Testing:

  • Acceptance tests for Config

Documentation:

  • "apm" -> "apm commands" in short desctiption
  • Broader usage documentation. The entities help, for example, just says "entities commands".
  • entities available commands have bad short descriptions
  • conventions around help messages
  • Should provide more full examples for usage. What's a revision?
  • Log format is not lovely.
  • "Help about any command" is upper cased. Need more love here on the short text.
  • apm available commands have bad short descriptions
  • no success message on profile delete
  • add examples for all command

Refactor:

  • refactor away from anonymous funcs for Run fields in commands
  • profile uses inconsistent casing for API: adminAPIKey, apiKey
  • replace fmt messages with log
  • make sure to wrap core errors with something more user friendly. case in point, passing a string to app id for deployments
  • Address duplication of errors (top & bottom of stderr output)
  • better looking formatter for logrus
  • brainstorm on command aliases and fill them out

Windows testing

Objective

The install and use of the tool should be tested on Windows.

Acceptance Criteria

  • Installation tested
  • Functionality has been tested
  • Powershell completion has been tested.

Docker hub image and associated docs

Objective

A docker image is available for users to download and use.

Acceptance Criteria

  • A docker image is available
  • Documentation about the use of the image and any caveats about the image are readily available to the user.

Refactor/test coverage backfill: Config

Blocked by #13.

Objective/AC

Currently we don't have a suite of tests for the config package. Similar to what we're doing in the credentials package, we should test for the following scenarios to make sure we handle with grace.

  • No ~/.newrelic/config.json in place by the user results in a pleasant error, or that we actually generate the file. Test the results.
  • Test that environment variables actually override the values from the configuration. This should enable docker run etc to be more useful.
  • Test the config set/etc commands to ensure that the values are written as we expect and we are able to read them as expected.

Homebrew recipe and associated docs

Objective

Homebrew users are able to install and learn about the CLI.

Acceptance Criteria

  • A brew formula is available to users
  • Documentation about the brew formula is available to users
  • Any caveats to using the brew formula are readily available to users of Homebrew

Filter result attribute set

Feature Description

Add the ability to filter the result set to specific fields returned by an Entity Search or other CLI commands that fetch data.

Create a getting started guide

Blocked on #83.
Related to #82.
Related to #80.

AC:

  • Create a use case-based getting started guide in the README or linked from the README
  • Use case: Searching an APM application entity by name, retrieving its application ID, and adding an entity tag to it

Implement config management

Feature Description

The following commands should be supported:

  • config set
  • config list
  • config delete
  • config get

The commands' behaviors should match that of the NR1 CLI.

APM get application command

Feature Description

Currently there is not an apm get command to retrieve an application object. Here we seek to create one.

Describe Alternatives

Search for an application and use jq to filter down. List applications and use jq to filter down.

--help should work without credentials/config/default-profile

Description

Currently, unless the three items above are set in the user environment, the user is unable to get help using the CLI. We should improve the error handling here to give the user some next steps. Also, we should document this in the README.

Current behavior

Without this, --help fails with "no configuration found" and does not display the help.

Expected behavior

--help for a new install should produce something useful for the user to get started. Perhaps this means creating new configuration files.

Steps To Reproduce

Steps to reproduce the behavior:

  1. rm -rf ~/.newrelic
  2. ./bin/darwin/newrelic --help

Related to #12

Write integration tests for the config package

Currently we don't have a suite of tests for the config package. Similar to what we're doing in the credentials package, we should test for the following scenarios to make sure we handle with grace.

  • No ~/.newrelic/config.json in place by the user results in a pleasant error, or that we actually generate the file. Test the results.
  • Test that environment variables actually override the values from the configuration. This should enable docker run etc to be more useful.
  • Test the config set/etc commands to ensure that the values are written as we expect and we are able to read them as expected.

Add additional entity search parameters

Entity search only allows for a name parameter currently, though more search parameters are provided by the client.

AC:

  • If possible, add the following optional search parameters to the CLI's entity search command:
    • alert severity
    • domain
    • infrastructure integration type
    • reporting
    • tags
    • type

Project artifacts: Architectural overview/diagram/README

Objective

Appropriately document the CLI architecture and update the README with any information needed to bring the project to a state where it can be published publicly.

Acceptance criteria

  • README is updated with project information and a getting started guide

Command contract refactor

Objective

Conform to words and style that are less offensive to the team.

Acceptance Criteria

  • Verbs after nouns
  • Prefer subcommands over hyphens
  • Eliminate use of “describe”
  • “Add tags” rather than “create tags” (follow what is in NG)
  • Determine a name for the CLI command and rename if it’s changing from “newrelic”

Implement deployment marker creation

Objective

Support deployment marker creation via the CLI.

Acceptance Criteria

  • Add a deployments subcommand for creating a deployment marker
  • Provide help and example command invocation
  • CLI error code should match success/failure of the operation

Notes

Potential command structure:
newrelic apm create-deployment --applicationId <appID> --id <id>

Accept input via command chaining

Feature Description

Add the ability to chain newrelic commands together, example would be an entity search filtered to GUIDs, then piped back to newrelic to add tags to all of those entities.

$ newrelic entity search --name "mystuff" --only-attributes entityId | \
  newrelic entity tags add --tag owner:me

Add ability to execute raw GraphQL query

Objective

To provide flexibility for the user, the CLI should offer the ability to execute raw GraphQL queries.

Acceptance Criteria

  • Query command should support simple GraphQL queries as well as complex queries that may include variables.

Examples

newrelic nerdgraph query "{ actor { user { email id name } } }"
newrelic nerdgraph query 'query($guid: EntityGuid!) { actor { entity(guid: $guid) { guid name domain entityType } } }' --variables '{"guid": "<GUID>"}'

Implement deployment marker deletion

Objective

Support deployment marker deletion via the CLI.

Acceptance Criteria

  • Add a deployments subcommand for deleting a deployment marker
  • Provide help and example command invocation
  • CLI error code should match success/failure of the operation

Notes

Potential command structure:
newrelic apm delete-deployment --applicationId <appID> --id <id>

Refactor to a request-based API

Objective

As the needs of the APIs and API keys change over time, we'd like to be in a position where, for each API method, we would be able to select the "style" of API to use. In some cases, even within a single package, we might want to implement GraphQL, while perhaps in a legacy method we might want to ensure we only ever use the V2 API.

Acceptance Criteria

  • The determination about which client pattern to use is easily surfaced when writing a new method.

Implement graceful shutdown for plugins

The plugin spike is throwing an error on exit that makes it seem like the graceful shutdown is not being performed by the plugin host. Let's figure out how to make this happen.

Implement entity tag deletion

Objective

Support Entity Tag deletion via the CLI.

Acceptance Criteria

Notes

Potential command structure:
newrelic entities delete-tags --guid <guid> --tags tag1,tag2
`newrelic entities delete-tag-values --guid --value tag1:value1 --value tag2:value2

Spike 2-way communication via stdin/stdout/stderr to a plugin via the plugin host

Currently the plugin is only able to communicate with the plugin host via stderr and stdout streams represented in the protobuf definition. The plugin host should support sending stdin to the plugin as well, so that the plugin can provide its own interactivity.

AC:

  • Allow stdin to be sent to the plugin via the plugin host

Notes:

  • Hashicorp's go-plugin module also has another built-in mechanism for streaming stdout/stderr back to the plugin host. We should explore if this is worth using instead of the protobuf contract.

Implement entity tag creation

Objective

Support Entity Tag creation/update via the CLI.

Acceptance Criteria

  • Add an entities subcommand for creating tags on an entity via entity guid
  • Add an entities subcommand for replacing tags on an entity via entity guid
  • CLI error code should match success/failure of the operation

Notes

Potential command structure:
newrelic entities create-tags --guid <guid> --tag tag1:value1 --tag tag1:value2 --tag tag2:value2, --tag2:value3

newrelic entities replace-tags --guid <guid> --tag tag1:value2 --tag tag2:value1

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.