@@ -92,102 +92,63 @@ module Rails {
9292}
9393
9494/**
95- * A reference to either `Rails::Railtie`, `Rails::Engine`, or `Rails::Application`.
95+ * Gets a reference to the `Rails` constant.
96+ */
97+ private DataFlow:: ConstRef rails ( ) { result = DataFlow:: getConst ( "Rails" ) }
98+
99+ /**
100+ * Gets a reference to either `Rails::Railtie`, `Rails::Engine`, or `Rails::Application`.
96101 * `Engine` and `Application` extend `Railtie`, but may not have definitions present in the database.
97102 */
98- private class RailtieClassAccess extends ConstantReadAccess {
99- RailtieClassAccess ( ) {
100- this .getScopeExpr ( ) .( ConstantAccess ) .getName ( ) = "Rails" and
101- this .getName ( ) = [ "Railtie" , "Engine" , "Application" ]
102- }
103+ private DataFlow:: ConstRef railtie ( ) {
104+ result = rails ( ) .getConst ( [ "Railtie" , "Engine" , "Application" ] )
103105}
104106
105- // A `ClassDeclaration` that (transitively) extends `Rails::Railtie`
106- private class RailtieClass extends ClassDeclaration {
107- RailtieClass ( ) {
108- this .getSuperclassExpr ( ) instanceof RailtieClassAccess or
109- exists ( RailtieClass other |
110- other .getModule ( ) = this .getSuperclassExpr ( ) .( ConstantReadAccess ) .getModule ( )
111- )
112- }
113- }
107+ /** Gets a class that transitively extends `Rails::Railtie` */
108+ private DataFlow:: ClassNode railtieClass ( ) { result = railtie ( ) .getADescendentModule ( ) }
114109
115- private DataFlow:: CallNode getAConfigureCallNode ( ) {
116- // `Rails.application.configure`
117- result = API:: getTopLevelMember ( "Rails" ) .getReturn ( "application" ) .getAMethodCall ( "configure" )
110+ /**
111+ * Gets a reference to `Rails::Application` or `Rails.application`.
112+ */
113+ private DataFlow:: LocalSourceNode railsApp ( ) {
114+ result = rails ( ) .getAMethodCall ( "application" )
118115 or
119- // `Rails::Application.configure`
120- exists ( ConstantReadAccess read , RailtieClass cls |
121- read = result .getReceiver ( ) .asExpr ( ) .getExpr ( ) and
122- read .getModule ( ) = cls .getModule ( ) and
123- result .asExpr ( ) .getExpr ( ) .( MethodCall ) .getMethodName ( ) = "configure"
124- )
116+ result = rails ( ) .getConst ( "Application" )
125117}
126118
127119/**
128120 * Classes representing accesses to the Rails config object.
129121 */
130122private module Config {
131- /**
132- * An access to a Rails config object.
133- */
134- private class SourceNode extends DataFlow:: LocalSourceNode {
135- SourceNode ( ) {
136- // `Foo < Rails::Application ... config ...`
137- exists ( MethodCall configCall | this .asExpr ( ) .getExpr ( ) = configCall |
138- configCall .getMethodName ( ) = "config" and
139- configCall .getEnclosingModule ( ) instanceof RailtieClass
140- )
141- or
142- // `Rails.application.config`
143- this = API:: getTopLevelMember ( "Rails" ) .getReturn ( "application" ) .getReturn ( "config" ) .asSource ( )
144- or
145- // `Rails.application.configure { ... config ... }`
146- // `Rails::Application.configure { ... config ... }`
147- exists ( DataFlow:: CallNode configureCallNode , Block block , MethodCall configCall |
148- configCall = this .asExpr ( ) .getExpr ( )
149- |
150- configureCallNode = getAConfigureCallNode ( ) and
151- block = configureCallNode .asExpr ( ) .getExpr ( ) .( MethodCall ) .getBlock ( ) and
152- configCall .getParent + ( ) = block and
153- configCall .getMethodName ( ) = "config"
154- )
155- }
156- }
157-
158- /**
159- * A reference to the Rails config object.
160- */
161- class Node extends DataFlow:: Node {
162- Node ( ) { exists ( SourceNode src | src .flowsTo ( this ) ) }
123+ DataFlow:: LocalSourceNode configSource ( ) {
124+ // `Foo < Rails::Application ... config ...`
125+ result = railtieClass ( ) .getAnOwnModuleSelf ( ) .getAMethodCall ( "config" )
126+ or
127+ // `Rails.application.config`
128+ result = railsApp ( ) .getAMethodCall ( "config" )
129+ or
130+ // TODO: move away from getParent+() when have better infrastructure for overridden 'self' in blocks
131+ // `Rails.application.configure { ... config ... }`
132+ // `Rails::Application.configure { ... config ... }`
133+ exists ( Block block , MethodCall configCall | configCall = result .asExpr ( ) .getExpr ( ) |
134+ block = railsApp ( ) .getAMethodCall ( "configure" ) .getBlock ( ) .asExpr ( ) .getExpr ( ) and
135+ configCall .getParent + ( ) = block and
136+ configCall .getMethodName ( ) = "config"
137+ )
163138 }
164139
165140 /**
166- * A reference to the ActionController config object.
141+ * Gets a reference to the ActionController config object.
167142 */
168- class ActionControllerNode extends DataFlow:: Node {
169- ActionControllerNode ( ) {
170- exists ( DataFlow:: CallNode source |
171- source .getReceiver ( ) instanceof Node and
172- source .getMethodName ( ) = "action_controller"
173- |
174- source .flowsTo ( this )
175- )
176- }
143+ DataFlow:: LocalSourceNode actionController ( ) {
144+ result = configSource ( ) .getAMethodCall ( "action_controller" )
177145 }
178146
179147 /**
180- * A reference to the ActionDispatch config object.
148+ * Gets a reference to the ActionDispatch config object.
181149 */
182- class ActionDispatchNode extends DataFlow:: Node {
183- ActionDispatchNode ( ) {
184- exists ( DataFlow:: CallNode source |
185- source .getReceiver ( ) instanceof Node and
186- source .getMethodName ( ) = "action_dispatch"
187- |
188- source .flowsTo ( this )
189- )
190- }
150+ DataFlow:: LocalSourceNode actionDispatch ( ) {
151+ result = configSource ( ) .getAMethodCall ( "action_dispatch" )
191152 }
192153}
193154
@@ -200,12 +161,11 @@ private module Settings {
200161 loc .getFile ( ) .getStem ( ) = "test"
201162 }
202163
203- private class Setting extends DataFlow:: CallNode {
164+ private class Setting extends DataFlow:: SetterCallNode {
204165 Setting ( ) {
205166 // exclude some test configuration
206167 not isInTestConfiguration ( this .getLocation ( ) ) and
207- this .getReceiver + ( ) instanceof Config:: Node and
208- this .asExpr ( ) .getExpr ( ) instanceof SetterMethodCall
168+ this = Config:: configSource ( ) .getAMethodCall + ( )
209169 }
210170 }
211171
@@ -257,8 +217,7 @@ private module Settings {
257217private class AllowForgeryProtectionSetting extends Settings:: BooleanSetting ,
258218 CsrfProtectionSetting:: Range {
259219 AllowForgeryProtectionSetting ( ) {
260- this .getReceiver ( ) instanceof Config:: ActionControllerNode and
261- this .getMethodName ( ) = "allow_forgery_protection="
220+ this = Config:: actionController ( ) .getAMethodCall ( "allow_forgery_protection=" )
262221 }
263222
264223 override boolean getVerificationSetting ( ) { result = this .getValue ( ) }
@@ -272,8 +231,7 @@ private class AllowForgeryProtectionSetting extends Settings::BooleanSetting,
272231private class EncryptedCookieCipherSetting extends Settings:: StringlikeSetting ,
273232 CookieSecurityConfigurationSetting:: Range {
274233 EncryptedCookieCipherSetting ( ) {
275- this .getReceiver ( ) instanceof Config:: ActionDispatchNode and
276- this .getMethodName ( ) = "encrypted_cookie_cipher="
234+ this = Config:: actionDispatch ( ) .getAMethodCall ( "encrypted_cookie_cipher=" )
277235 }
278236
279237 OpenSslCipher getCipher ( ) { this .getValueText ( ) = result .getName ( ) }
@@ -293,8 +251,7 @@ private class EncryptedCookieCipherSetting extends Settings::StringlikeSetting,
293251private class UseAuthenticatedCookieEncryptionSetting extends Settings:: BooleanSetting ,
294252 CookieSecurityConfigurationSetting:: Range {
295253 UseAuthenticatedCookieEncryptionSetting ( ) {
296- this .getReceiver ( ) instanceof Config:: ActionDispatchNode and
297- this .getMethodName ( ) = "use_authenticated_cookie_encryption="
254+ this = Config:: actionDispatch ( ) .getAMethodCall ( "use_authenticated_cookie_encryption=" )
298255 }
299256
300257 boolean getDefaultValue ( ) { result = true }
@@ -316,8 +273,7 @@ private class UseAuthenticatedCookieEncryptionSetting extends Settings::BooleanS
316273private class CookiesSameSiteProtectionSetting extends Settings:: NillableStringlikeSetting ,
317274 CookieSecurityConfigurationSetting:: Range {
318275 CookiesSameSiteProtectionSetting ( ) {
319- this .getReceiver ( ) instanceof Config:: ActionDispatchNode and
320- this .getMethodName ( ) = "cookies_same_site_protection="
276+ this = Config:: actionDispatch ( ) .getAMethodCall ( "cookies_same_site_protection=" )
321277 }
322278
323279 string getDefaultValue ( ) { result = "lax" }
0 commit comments