KEMBAR78
FSD Answers | PDF | Databases | Mongo Db
0% found this document useful (0 votes)
40 views36 pages

FSD Answers

The document provides a comprehensive overview of REST API and GraphQL, highlighting their differences in architecture, data fetching efficiency, and developer experience. It explains the advantages of GraphQL's introspection and schema documentation tools, as well as the integration of List and Create APIs in applications. Additionally, it covers MongoDB's data structure, aggregation pipeline, and the comparison between using the native Node.js driver and Mongoose for database operations.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
40 views36 pages

FSD Answers

The document provides a comprehensive overview of REST API and GraphQL, highlighting their differences in architecture, data fetching efficiency, and developer experience. It explains the advantages of GraphQL's introspection and schema documentation tools, as well as the integration of List and Create APIs in applications. Additionally, it covers MongoDB's data structure, aggregation pipeline, and the comparison between using the native Node.js driver and Mongoose for database operations.
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 36

1.

Define REST API and di erentiate it from GraphQL


REST (Representational State Transfer) is an architectural style used to design networked
applications. It organizes interactions around resources, which are identified using URLs, and
uses standard HTTP methods to perform operations on those resources.

REST is stateless—each request must contain all necessary information, and the server doesn’t
store client context between requests.

Example: Getting a user's data using REST

What is GraphQL?

GraphQL is a query language for APIs and a runtime for fulfilling those queries. Unlike REST, it uses
a single endpoint and allows clients to specify exactly what data they need, reducing over-
fetching and under-fetching.

Example: Getting the same user data using GraphQL


Single Endpoint Request:

Response:
Key Di erences (with Context)

Feature REST API GraphQL

Endpoints Multiple: /users, /users/:id/orders Single: /graphql

Data Fetching May require multiple requests Single query fetches related nested data

Returns fixed structures (all


Over-fetching Returns only requested fields
fields)

Versioning Needs URL versioning (e.g., /v1/) Evolving schema avoids versioning

Data No strict schema; client must Strongly typed schema with


Types/Schema infer introspection

2. Explain how introspection and schema


documentation tools like GraphiQL enhance
development productivity in GraphQL.
GraphQL o ers a powerful feature called introspection, which allows clients to query the API for
details about its schema—such as types, fields, and operations (queries and mutations). This self-
awareness enables tools like GraphiQL, GraphQL Playground, and Apollo Studio Explorer to
provide interactive, real-time documentation and testing environments that significantly boost
developer productivity.

Key Benefits

1. Self-Documenting APIs

GraphQL schemas are inherently self-documenting. With introspection, tools can automatically
fetch and display:

 Available queries and mutations

 Input arguments and return types

 Descriptions and deprecation notices (if defined in schema)

Example Introspection Query:


Sample Response:

2. Schema Exploration

Tools like GraphiQL and GraphQL Playground o er sidebar explorers, autocomplete, and type
tooltips—making it easy for developers to understand the structure, relationships, and
capabilities of the API without reading a manual.

3. Interactive Query Testing

Developers can compose, run, and debug queries and mutations in real time:

 No need for separate Postman setups or frontend code

 Syntax highlighting, auto-suggestions, and inline error feedback streamline testing


Example Usage in GraphiQL:

4. Always Up-to-Date Documentation

Because introspection reflects the current schema, tools built on it always display the latest API
structure—no more syncing separate documentation when the API changes.

3. Di erentiate between List API and Create API


integration with suitable examples.
1. List API Integration (Read Operation)

Purpose:

To fetch and display data (e.g., a list of issues) from the GraphQL server and render it in the UI.

Key Actions:

 Define a GraphQL query

 Use fetch() to send the query to the server

 Update the UI with the retrieved data

 Remove hardcoded/static data

Example Code (JavaScript with React):


Outcome:

 Fetches a list of issues

 Populates the component’s state

 Automatically re-renders the UI

2. Create API Integration (Write Operation)

Purpose:

To add a new issue to the database by sending a GraphQL mutation, then refresh the list from the
server.

Key Actions:

 Capture user input

 Construct a GraphQL mutation

 Use fetch() to send the mutation along with variables

 Call loadData() again to refresh the list

Example Code (JavaScript with React):


Example Input:

Outcome:

 Sends a mutation to add a new issue

 Data is persisted on the server (e.g., in MongoDB)

 The UI reloads the updated issue list from the server

Summary Table

Feature List API Create API

Operation Type Query (Read) Mutation (Write)


Feature List API Create API

Use Case Display existing issues Add a new issue

GraphQL Example query { issueList { id title ... } } mutation AddIssue($issue: IssueInputs!)

Input Required? No Yes (user input for new issue)

Response Set state with


Call loadData() to reload updated list
Handling result.data.issueList

Writes data to DB and fetches updated


Persistence Reads data from DB
state

4. Compare and contrast REST API and GraphQL in


terms of performance, data fetching e iciency, and
developer experience
1. Performance & Data Fetching E iciency

Feature REST API GraphQL

Common—returns full resource objects, Avoided—client specifies exactly


Over-fetching
even if the client needs only part which fields are needed

Requires multiple endpoints to retrieve Solved—can fetch deeply nested


Under-fetching
related data related data in a single query

Example To get a user and their issues: /users/1 + One query: { user(id: 1) { name,
Scenario /users/1/issues issues { id, title } } }

Network Smaller payloads and single


Higher payloads and round-trips
E iciency request for complex objects

Mobile More e icient—only needed data


Less e icient—more data transfer
Optimization transferred

Verdict:

GraphQL outperforms REST when minimizing data transfer and reducing the number of requests
needed, especially for nested or related data.
2. Developer Experience

Feature REST API GraphQL

Multiple per resource: /users,


Endpoints Single endpoint: /graphql
/issues, /issues/:id/comments, etc.

No built-in discoverability; requires Self-documenting via introspection;


Schema
documentation (Swagger, Postman, tools like GraphQL Playground or Apollo
Discoverability
etc.) Studio enable schema browsing

Limited by backend-defined Highly flexible—clients shape their


Query Flexibility
endpoints queries based on needs

Error structure varies across


Error Handling Unified and descriptive error format
endpoints

Strong IDE support, autocompletion,


Tooling Support Varies depending on the ecosystem
and query validation via schema

Typing & Weak typing unless combined with Strongly typed schema enforces
Validation external tools contract between client and server

Verdict:

GraphQL o ers a superior developer experience due to its schema introspection, flexibility,
and robust tooling, especially for front-end and full-stack developers.

Summary Table

Aspect REST API GraphQL

Data Fetching Over/under-fetching common Fetches exactly what is needed

Number of Multiple for nested/related


Single request for deeply nested data
Requests resources

Payload Size Often large (fixed fields) Minimal (custom fields)

Endpoints Multiple endpoints Single endpoint

Documentation External tools needed Self-documented schema


Aspect REST API GraphQL

Query Flexibility Defined by backend Defined by client

Tooling Support Depends on API ecosystem Excellent (GraphQL Playground, Apollo, etc.)

Higher (requires learning query syntax and


Learning Curve Lower (familiar HTTP verbs)
schema types)

5. Illustrate how to use MongoDB query language to


filter documents based on nested fields and array
values.
MongoDB stores data in BSON format (a binary representation of JSON), allowing documents to
contain nested objects and arrays. This flexible schema design enables rich and hierarchical
data models.

Sample Document (Invoice Collection)


In this document:

 billingAddress is a nested object

 items is an array of embedded objects

Querying Nested Fields

To query a nested field, MongoDB uses dot notation to reach into the structure.

Example 1: Filter by Nested Field (billingAddress.city)

Goal: Find all invoices where the billing city is New York.

Example 2: Filter by Nested Field with Operator

Goal: Find invoices where the billing ZIP code is greater than 10000.

Note: ZIP codes are typically stored as strings, so string comparison rules apply unless you
convert them to numbers.

Querying Arrays of Values and Objects

Example 3: Filter by Array Element Value

Goal: Find invoices that include Widget A in their items.


This works because MongoDB automatically checks each object in the items array for a match on
description.

Querying with Multiple Conditions in Array Objects

Example 4: Match Specific Conditions Within an Array Element

Goal: Find invoices with an item where:

 description is "Widget B"

 and price is greater than 40

$elemMatch ensures that both conditions apply to the same object within the array.

Filtering Based on Array Length or Exact Match

Example 5: Find Invoices with Exactly Two Items


6. Explain the MongoDB aggregation pipeline with
syntax and examples. Include at least two stages.
What is the MongoDB Aggregation Pipeline?

The MongoDB aggregation pipeline is a powerful data processing framework used to transform,
filter, analyze, and reshape data in a collection. It is conceptually similar to Unix pipelines and
SQL's GROUP BY, WHERE, and SELECT, but much more flexible.

Core Syntax

Each stage is an operation (represented as a document) that transforms the data. The output of
one stage becomes the input for the next.

Key Stages with Syntax and Examples

1. $match Stage — Filtering Data

Purpose:

Filters documents based on specific conditions, like WHERE in SQL. It's best placed early in the
pipeline to reduce processing cost.

Syntax:

Example:

Find employees whose age is greater than 30.


This filters the documents so that only those with age > 30 proceed to the next stage.

2. $group Stage — Aggregating Data

Purpose:

Groups documents by a field and performs aggregation like sum, average, min, max, count, etc.

Syntax:

Example A: Sum of All Ages

Group all documents together (_id: null) and sum their age values.
Example B: Average Age by Organization

Group by the organization field and compute the average age.

Combining $match and $group

You can chain $match and $group to first filter and then aggregate the result set.

Example C: Average Age of Employees Over 30, Grouped by Organization

7. Describe the role of documents, collections, and


databases in MongoDB. How do they relate to each
other?
In MongoDB, data is organized using a three-tier hierarchy: Databases → Collections →
Documents. Each level serves a distinct role and contributes to MongoDB's flexible, scalable, and
schema-less architecture. Here's a detailed explanation of each component and how they relate:

1. Documents

 Role:
The document is the fundamental unit of data in MongoDB.

 Structure:

o Stored in a BSON (Binary JSON) format.

o Consists of field-value pairs (like JSON objects).

o Fields can hold:

 Primitive types: strings, numbers, booleans, dates, etc.

 Embedded documents: objects within objects.

 Arrays: lists of values or even other documents.

 Example:

"_id": ObjectId("65f1a2b8c1f3d6"),

"name": "Alice",

"age": 28,

"address": {

"city": "Bangalore",

"zip": "560001"

},

"hobbies": ["reading", "cycling"]

 Key Features:

o Every document must have a unique _id field.


o Provides flexibility — documents in the same collection can have di erent fields or
structures.

o Embedded data means faster reads — often no need for joins.

2. Collections

 Role:
A collection is a group of related documents, similar to a table in relational databases.

 Characteristics:

o No schema enforcement by default (i.e., schema-less).

o Optional schema validation can be added to enforce structure.

o You can create indexes on any field to improve performance, including those inside
embedded documents or arrays.

 Example:
A collection called users might contain multiple documents like:

{ "name": "Alice", "age": 28 }

{ "name": "Bob", "email": "bob@example.com" }

 Flexibility:

o Unlike SQL tables, documents in a collection don't need to have the same set of
fields or types.

o Collections are dynamically created upon first insert.

3. Databases

 Role:
A database is a logical container for one or more collections.

 Behavior:

o Similar to a database in SQL, but without foreign keys or enforced relationships.

o Mainly used for namespace separation (e.g., separate databases for di erent
applications or environments).

o A MongoDB instance can host multiple databases.


 Commands:

o List databases:

show dbs

o Switch to a database (or create one on the fly):

use ecommerce

 Isolation:

o Collections in di erent databases are isolated from each other.

o You typically operate within a single database per connection.

8. Compare and contrast reading and writing data to


MongoDB using the native Node.js driver versus
Mongoose.
When working with MongoDB in a Node.js application, you have two primary options:

1. MongoDB Native Node.js Driver – A low-level, direct interface to the database.

2. Mongoose – An Object Document Mapper (ODM) that adds structure and abstraction on
top of the native driver.

Here's a detailed comparison and contrast of both, based on the provided information and
expanded with practical insights:

1. MongoDB Native Node.js Driver

Description

 O icial driver maintained by the MongoDB team.

 O ers direct access to MongoDB operations with minimal abstraction.

 Requires manual control over schemas, validation, and relationships.

Reading Data

const client = new MongoClient(uri);

await client.connect();
const db = client.db("shop");

const products = await db.collection("products").find({ category: "books" }).toArray();

Writing Data

await db.collection("products").insertOne({

name: "Node.js Guide",

price: 20,

category: "books"

});

Advantages

 Fine-grained control: You interact directly with collections and documents.

 Lightweight: No extra layers or abstraction.

 Good for learning MongoDB fundamentals.

Disadvantages

 No schema enforcement (unless you add your own validation logic).

 More boilerplate for tasks like relationships, hooks, and validations.

 Less intuitive for complex applications.

2. Mongoose (ODM)

Description

 A high-level ODM (Object Data Mapper) for MongoDB.

 Adds schema, models, validation, and middleware.

 Ideal for applications where structure, relationships, and data consistency are important.

Reading Data

const Product = mongoose.model("Product", productSchema);

const books = await Product.find({ category: "books" });

Writing Data
const newProduct = new Product({

name: "Node.js Guide",

price: 20,

category: "books"

});

await newProduct.save();

Advantages

 Schema enforcement: Define and validate document structure up front.

 Built-in utilities: Relationships (populate()), hooks (pre, post), and validation.

 Cleaner syntax: Especially helpful for large apps.

Disadvantages

 More abstraction: You may not see how MongoDB really works under the hood.

 Performance overhead: Slightly heavier due to features like casting and validation.

 Less flexible: Sometimes gets in the way of custom MongoDB features (like aggregations)

9. Explain the process of integrating a List API with a


front-end React component.
Integrating a List API—such as a GraphQL endpoint—into a front-end React component (like
IssueList) transforms a static UI into a dynamic, data-driven one. Here's a step-by-step breakdown
based on your summary, with explanations and code-style examples for clarity:

1. Establish the Goal

You want the IssueList React component to fetch live data from a GraphQL List API, replacing any
hardcoded or in-memory array of issues.

2. Modify the loadData() Method

This method is responsible for fetching issues from the server. Initially, it may just return static
data:
loadData() {

this.setState({ issues: initialIssues });

Replace it with a method that fetches from the API.

3. Construct the GraphQL Query

Define the query to request specific fields from the API. Use a template literal:

const query = `

query {

issueList {

id title status owner

created e ort due

`;

4. Make the API Request Using fetch()

Use fetch() with POST to call the GraphQL endpoint, e.g., /graphql.

async function graphQLFetch(query, variables = {}) {

try {

const response = await fetch('/graphql', {

method: 'POST',

headers: { 'Content-Type': 'application/json' },

body: JSON.stringify({ query, variables }),

});

const body = await response.json();

if (body.errors) {
alert(`GraphQL error: ${body.errors[0].message}`);

return body.data;

} catch (e) {

alert(`Network error: ${e.message}`);

return null;

5. Handle the API Response

Call graphQLFetch() inside loadData() and handle the returned data:

async loadData() {

const query = `...`; // Same as above

const data = await graphQLFetch(query);

if (data) {

this.setState({ issues: data.issueList });

6. Update Component State

You use this.setState() to update React state so that the component re-renders:

this.setState({ issues: data.issueList });

Never modify this.state directly—always use setState().

7. Handle Data Type Di erences

If dates are returned as ISO strings, format them accordingly:

<td>{new Date(issue.created).toDateString()}</td>
Or convert them earlier when setting state.

8. Trigger Data Fetching in componentDidMount()

Use React lifecycle method componentDidMount() to trigger the first data load:

componentDidMount() {

this.loadData();

This ensures the API request is made after the component is mounted.

9. Remove Hardcoded Data

Once live API data works, remove any:

const initialIssues = [ /* hardcoded array */ ];

This prevents outdated or duplicate rendering.

10. Implement Error Handling

Use try-catch around your fetch logic and check for errors in the API response:

if (body.errors) {

// show a UI error, alert, or fallback message

11. Verify Integration

After completing these steps:

 Reload the browser

 You should see data fetched from the live backend

 Changes in the DB (e.g., new issues) should reflect automatically after refresh
Example Recap: Full loadData() with Integration

And in componentDidMount():

10. Describe introspection in GraphQL and its utility in


schema exploration.
What is Introspection in GraphQL?

Introspection refers to the ability to:

 Query meta-information about the schema (types, fields, arguments, queries, mutations,
etc.)

 Use special system fields like __schema, __type, __typename, etc.

Example Introspection Query:


This query returns a list of all types in the schema and details about the root query and mutation
types.

Utility in Schema Exploration

Introspection plays a critical role in development workflows:

1. Self-Documentation

 Developers can understand available operations (queries/mutations/subscriptions)


without needing external docs.

 Enables dynamic UI generation (e.g., dropdowns for queryable fields).

2. GraphQL IDE Support

Tools like:

 GraphiQL

 Apollo Sandbox / Apollo Studio

 Insomnia

 Postman (GraphQL mode)

...rely on introspection to:

 Auto-complete fields

 Show field descriptions and types

 O er interactive schema explorers


3. API Exploration Without Backend Knowledge

 Frontend devs can explore APIs without needing backend hand-holding.

 Easily check what data is available, what arguments are accepted, and what types are
returned.

4. Tooling and Codegen

 Tools like graphql-codegen, Apollo Codegen, and Relay Compiler use introspection results
to:

o Generate type-safe client code

o Create documentation

o Validate queries statically

Security Consideration

 In production, some servers disable introspection to avoid exposing internal API


structures to attackers.

o Tools like graphql-shield can allow it in dev but restrict it in prod.

11. Explain the CRUD operations in MongoDB with


syntax and examples.
1. Create – Insert Documents

➤ insertOne(): Insert a single document

Syntax:

db.employees.insertOne({ id: 1, name: { first: 'John', last: 'Doe' }, age: 44 });

Node.js Example (async/await):

const result = await db.collection('employees').insertOne({ id: 1, name: { first: 'John', last: 'Doe' },
age: 44 });

console.log(result.insertedId);

➤ insertMany(): Insert multiple documents

Syntax:
db.employees.insertMany([

{ id: 2, name: { first: 'Jane', last: 'Doe' }, age: 30 },

{ id: 3, name: { first: 'Mark', last: 'Smith' }, age: 35 }

]);

In applications like issue trackers, you often generate custom unique IDs using a counter
collection with findOneAndUpdate() before calling insertOne().

2. Read – Retrieve Documents

➤ findOne(): Get a single document

Syntax: db.employees.findOne({ id: 1 });

➤ find(): Get multiple documents

Syntax: db.employees.find({ age: { $gte: 30 } });

Node.js Example:

const issues = await db.collection('issues').find({}).toArray();

console.log(issues);

➤ Common Filter Operators:

 { age: { $gte: 30 } } → age ≥ 30

 { name: "John" } → exact match

 { invoiceNumber: { $gt: 1000 } } → invoiceNumber > 1000

In the issueList() API function, find({}).toArray() is used to fetch all issues from the MongoDB
database.

3. Update – Modify Documents

➤ updateOne(): Update a single matching document

Syntax: db.employees.updateOne({ id: 1 }, { $set: { age: 45 } });

➤ updateMany(): Update all matching documents

Syntax: db.employees.updateMany({}, { $set: { organization: 'MyCompany' } });


➤ replaceOne(): Replace an entire document

Syntax: db.employees.replaceOne({ id: 1 }, { id: 1, name: 'Updated Name', age: 50 });

$set is used to update only specific fields rather than replacing the whole document.

4. Delete – Remove Documents

➤ deleteOne(): Delete the first matching document

Syntax: db.employees.deleteOne({ id: 4 });

➤ deleteMany(): Delete all matching documents

Syntax: db.employees.deleteMany({ age: { $lt: 20 } });

➤ Clear all documents from a collection

db.employees.remove({});

12. Develop a Node.js program that performs all CRUD


operations on a MongoDB collection named students.
13. Develop a Create API in GraphQL that accepts an
object with custom scalar types, validates the input,
and returns appropriate errors if any.
1. Schema (schema.graphql)

2. Custom Scalar Implementation (graphql_date.js)


3. Mutation Resolver (resolvers.js)
4. Apollo Server Setup (server.js)

5. Example Mutation Query (client-side, with variables)


14. Write a sample schema for a GraphQL About API
including custom scalar types.
Here's a sample GraphQL schema for an About API including the definition of a custom scalar
type GraphQLDate. Although the About API itself only uses basic types (like String), the schema
also declares a custom scalar for dates to demonstrate how you can include it for use elsewhere
in your application:
Explanation:

 about: String! — Query to fetch the about message, guaranteed to return a string.

 setAboutMessage(message: String!): String — Mutation to update the about message;


accepts a mandatory message and returns the updated string.

 scalar GraphQLDate — Declaration of a custom scalar type for date handling. You will
implement this scalar’s behavior (parsing, serialization, validation) in your server resolvers.

This schema forms a simple About API while showing how to declare a custom scalar type in the
same schema file for future use.

15. What is a Graph-Based API? How does GraphQL


di er from traditional REST in terms of data
representation?
A Graph-Based API is an API that models and exposes data as a graph structure—where entities
(nodes) are interconnected through relationships (edges). This approach naturally represents
complex data and their interdependencies, allowing clients to query across related entities
seamlessly.

GraphQL is the most prominent example of a graph-based API. Instead of multiple endpoints
representing separate resources, GraphQL o ers a single endpoint where clients request exactly
the data they need, traversing relationships in a graph-like manner.

How does GraphQL di er from traditional REST in terms of data representation?

Aspect REST GraphQL

Graph-based: data as interconnected


Data Resource-based: distinct, self-contained
nodes and edges, representing objects
Model resources (e.g., /users, /orders).
and their relationships.

Multiple endpoints, each representing a Single endpoint (e.g., /graphql) serving


Endpoints
resource or action. all queries and mutations.
Aspect REST GraphQL

Often results in over-fetching (getting


Client specifies exactly which fields and
Data unnecessary data) or under-fetching
related data to fetch in one request—no
Fetching (requiring multiple requests to get related
over- or under-fetching.
data).

Less flexible, tied to predefined endpoints Highly flexible queries shaped by the
Flexibility
and payloads. client at runtime.

What is Introspection in GraphQL and its utility?

Introspection is a built-in feature of GraphQL servers that allows clients to query the API about its
own schema, types, fields, and operations.

Utility:

 Enables self-documenting APIs—clients can discover what queries, mutations, and types
are available dynamically.

 Powers developer tools like Apollo Playground or GraphiQL, providing interactive


exploration, autocompletion, and testing of API queries.

 Removes the dependency on separate, often outdated, external documentation.

 Facilitates rapid development by allowing developers to understand and adapt to API


changes quickly.

Introspection (Self-Documenting APIs)

GraphQL servers can describe their own schema dynamically.

o Developers can explore available queries and mutations without external


documentation.

o Tools like Apollo Playground allow real-time API exploration and testing.

Libraries

o Parsing and dealing with the type system language (also called the GraphQL
Schema Language) as well as the query language is hard to do on your own.

o Fortunately, there are tools and libraries available in most languages for this
purpose.
 For JavaScript on the back-end, there is a reference implementation of GraphQL
called GraphQL.js. To tie this to Express and enable HTTP requests to be the
transport mechanism for the API calls, there is a package called express-
graphql.

 But these are very basic tools that lack some advanced support such as
modularized schemas and seamless handling of custom scalar types.

 The package graphql-tools and the related apollo-server are built on top of
GraphQL.js to add these advanced features. We will be using the advanced
packages for the Issue Tracker application in this chapter.

 I will cover only those features of GraphQL that are needed for the purpose of the
application.

 For advanced features that you may need in your own specific application, do
refer to the complete documentation of GraphQL at https://graphql.org and the
tools at https://www.apollographql.com/ docs/graphql-tools/.

You might also like