Home > Back-end >  xpath for input based of its label
xpath for input based of its label

Time:05-28

I want to select an input, based of its label. I found below xpath, which returns 3 inputs, even though two of returned inputs have different labels. I want to understand why it works like that and how to improve it to return correct (one) input element. Here is the xpath:

//input[@id=(//label[.='Max Driving Time_h']/@for)]

And yes, I know I can get the proper input with xpath like this:

//label[.='Max Driving Time_h']/ancestor::div/input

I would just like to understand, what's wrong with the first xpath ;) Thank you in advance!

Here is the HTML code to try...

<!DOCTYPE html>
<html>
   <head>
      <title>Page Title</title>
   </head>
   <body>
      <div >
         <mat-tab-body role="tabpanel"  id="mat-tab-content-4-0" aria-labelledby="mat-tab-label-4-0">
            <div cdkscrollable=""  style="transform: none;">
               <!---->
               <div fxlayout="column" fxlayoutalign="space-between start" style="padding-top: 10px; flex-direction: column; box-sizing: border-box; display: flex; place-content: flex-start space-between; align-items: flex-start;" >
                  <dsg-input-duration >
                     <div flex-wrap="nowrap" style="display: inline-block; margin-right: 15px;" >
                        <div fxlayout="column" fxlayoutalign="start start"  style="flex-direction: column; box-sizing: border-box; display: flex; place-content: flex-start; align-items: flex-start;">
                           <div >Max Driving Time</div>
                           <div fxlayout="row" style="flex-direction: row; box-sizing: border-box; display: flex;">
                              <mat-form-field floatlabel="always" >
                                 <div >
                                    <div >
                                       <!----><!---->
                                       <div >
                                          <input matinput="" formcontrolname="hours" id="h" name="h" type="number" min="0" autocomplete="really-off"  aria-invalid="false" aria-required="false" max="23">
                                          <span >
                                             <label  id="mat-form-field-label-179" for="h" aria-owns="h">
                                                <!---->
                                                <mat-label style="visibility: hidden !important;" >Max Driving Time_h</mat-label>
                                                <!----><!---->
                                             </label>
                                             <!---->
                                          </span>
                                       </div>
                                       <!---->
                                    </div>
                                    <div ><span ></span></div>
                                    <!---->
                                    <div >
                                       <!---->
                                       <div  style="opacity: 1; transform: translateY(0%);">
                                          <!---->
                                          <div ></div>
                                       </div>
                                       <!---->
                                    </div>
                                 </div>
                              </mat-form-field>
                              <label for="h" >h</label>
                              <mat-form-field >
                                 <div >
                                    <div >
                                       <!----><!---->
                                       <div >
                                          <input matinput="" formcontrolname="minutes" id="m" name="m" type="number" min="0" max="59" autocomplete="really-off"  aria-invalid="false" aria-required="false">
                                          <span >
                                             <label  id="mat-form-field-label-181" for="m" aria-owns="m">
                                                <!---->
                                                <mat-label style="visibility: hidden !important; display: none;" >Max Driving Time_m</mat-label>
                                                <!----><!---->
                                             </label>
                                             <!---->
                                          </span>
                                       </div>
                                       <!---->
                                    </div>
                                    <div ><span ></span></div>
                                    <!---->
                                    <div >
                                       <!---->
                                       <div  style="opacity: 1; transform: translateY(0%);">
                                          <!---->
                                          <div ></div>
                                       </div>
                                       <!---->
                                    </div>
                                 </div>
                              </mat-form-field>
                              <label for="m" >m</label><!----><!---->
                           </div>
                           <div fxlayout="row" style="flex-direction: row; box-sizing: border-box; display: flex;">
                              <div fxlayout="column"  style="flex-direction: column; box-sizing: border-box; display: flex;">
                                 <!----><!----><!----><!----><!----><!----><!----><!----><!---->
                              </div>
                           </div>
                        </div>
                     </div>
                  </dsg-input-duration>
                  <dsg-input-duration >
                     <div flex-wrap="nowrap" style="display: inline-block; margin-right: 15px;" >
                        <div fxlayout="column" fxlayoutalign="start start"  style="flex-direction: column; box-sizing: border-box; display: flex; place-content: flex-start; align-items: flex-start;">
                           <div >Max Elapsed Time</div>
                           <div fxlayout="row" style="flex-direction: row; box-sizing: border-box; display: flex;">
                              <mat-form-field floatlabel="always" >
                                 <div >
                                    <div >
                                       <!----><!---->
                                       <div >
                                          <input matinput="" formcontrolname="hours" id="h" name="h" type="number" min="0" autocomplete="really-off"  aria-invalid="false" aria-required="false" max="23">
                                          <span >
                                             <label  id="mat-form-field-label-183" for="h" aria-owns="h">
                                                <!---->
                                                <mat-label style="visibility: hidden !important;" >Max Elapsed Time_h</mat-label>
                                                <!----><!---->
                                             </label>
                                             <!---->
                                          </span>
                                       </div>
                                       <!---->
                                    </div>
                                    <div ><span ></span></div>
                                    <!---->
                                    <div >
                                       <!---->
                                       <div  style="opacity: 1; transform: translateY(0%);">
                                          <!---->
                                          <div ></div>
                                       </div>
                                       <!---->
                                    </div>
                                 </div>
                              </mat-form-field>
                              <label for="h" >h</label>
                              <mat-form-field >
                                 <div >
                                    <div >
                                       <!----><!---->
                                       <div >
                                          <input matinput="" formcontrolname="minutes" id="m" name="m" type="number" min="0" max="59" autocomplete="really-off"  aria-invalid="false" aria-required="false">
                                          <span >
                                             <label  id="mat-form-field-label-185" for="m" aria-owns="m">
                                                <!---->
                                                <mat-label style="visibility: hidden !important; display: none;" >Max Elapsed Time_m</mat-label>
                                                <!----><!---->
                                             </label>
                                             <!---->
                                          </span>
                                       </div>
                                       <!---->
                                    </div>
                                    <div ><span ></span></div>
                                    <!---->
                                    <div >
                                       <!---->
                                       <div  style="opacity: 1; transform: translateY(0%);">
                                          <!---->
                                          <div ></div>
                                       </div>
                                       <!---->
                                    </div>
                                 </div>
                              </mat-form-field>
                              <label for="m" >m</label><!----><!---->
                           </div>
                           <div fxlayout="row" style="flex-direction: row; box-sizing: border-box; display: flex;">
                              <div fxlayout="column"  style="flex-direction: column; box-sizing: border-box; display: flex;">
                                 <!----><!----><!----><!----><!----><!----><!----><!----><!---->
                              </div>
                           </div>
                        </div>
                     </div>
                  </dsg-input-duration>
                  <dsg-input-duration >
                     <div flex-wrap="nowrap" style="display: inline-block; margin-right: 15px;" >
                        <div fxlayout="column" fxlayoutalign="start start"  style="flex-direction: column; box-sizing: border-box; display: flex; place-content: flex-start; align-items: flex-start;">
                           <div >Max Working Time</div>
                           <div fxlayout="row" style="flex-direction: row; box-sizing: border-box; display: flex;">
                              <mat-form-field floatlabel="always" >
                                 <div >
                                    <div >
                                       <!----><!---->
                                       <div >
                                          <input matinput="" formcontrolname="hours" id="h" name="h" type="number" min="0" autocomplete="really-off"  aria-invalid="false" aria-required="false" max="23">
                                          <span >
                                             <label  id="mat-form-field-label-187" for="h" aria-owns="h">
                                                <!---->
                                                <mat-label style="visibility: hidden !important;" >Max Working Time_h</mat-label>
                                                <!----><!---->
                                             </label>
                                             <!---->
                                          </span>
                                       </div>
                                       <!---->
                                    </div>
                                    <div ><span ></span></div>
                                    <!---->
                                    <div >
                                       <!---->
                                       <div  style="opacity: 1; transform: translateY(0%);">
                                          <!---->
                                          <div ></div>
                                       </div>
                                       <!---->
                                    </div>
                                 </div>
                              </mat-form-field>
                              <label for="h" >h</label>
                              <mat-form-field >
                                 <div >
                                    <div >
                                       <!----><!---->
                                       <div >
                                          <input matinput="" formcontrolname="minutes" id="m" name="m" type="number" min="0" max="59" autocomplete="really-off"  aria-invalid="false" aria-required="false">
                                          <span >
                                             <label  id="mat-form-field-label-189" for="m" aria-owns="m">
                                                <!---->
                                                <mat-label style="visibility: hidden !important; display: none;" >Max Working Time_m</mat-label>
                                                <!----><!---->
                                             </label>
                                             <!---->
                                          </span>
                                       </div>
                                       <!---->
                                    </div>
                                    <div ><span ></span></div>
                                    <!---->
                                    <div >
                                       <!---->
                                       <div  style="opacity: 1; transform: translateY(0%);">
                                          <!---->
                                          <div ></div>
                                       </div>
                                       <!---->
                                    </div>
                                 </div>
                              </mat-form-field>
                              <label for="m" >m</label><!----><!---->
                           </div>
                           <div fxlayout="row" style="flex-direction: row; box-sizing: border-box; display: flex;">
                              <div fxlayout="column"  style="flex-direction: column; box-sizing: border-box; display: flex;">
                                 <!----><!----><!----><!----><!----><!----><!----><!----><!---->
                              </div>
                           </div>
                        </div>
                     </div>
                  </dsg-input-duration>
                  <dsg-input-number controlname="maxDistance">
                     <div  style="display: inline-block;">
                        <mat-form-field floatlabel="always" >
                           <div >
                              <div >
                                 <!----><!---->
                                 <div >
                                    <input matinput="" type="number"  autofocus="" autocomplete="off" step="" id="maxDistance" data-placeholder="" aria-invalid="false" aria-required="false" min="-Infinity" max="2147483647" maxlength="14">
                                    <span >
                                       <label  id="mat-form-field-label-191" for="maxDistance" aria-owns="maxDistance">
                                          <!---->
                                          <mat-label >Max Distance [km]</mat-label>
                                          <!----><!---->
                                       </label>
                                       <!---->
                                    </span>
                                 </div>
                                 <!---->
                              </div>
                              <div ><span ></span></div>
                              <!---->
                              <div >
                                 <!---->
                                 <div  style="opacity: 1; transform: translateY(0%);">
                                    <!---->
                                    <div ></div>
                                 </div>
                                 <!---->
                              </div>
                           </div>
                        </mat-form-field>
                     </div>
                  </dsg-input-number>
               </div>
               <!---->
            </div>
         </mat-tab-body>
         <mat-tab-body role="tabpanel"  id="mat-tab-content-4-1" aria-labelledby="mat-tab-label-4-1">
            <div cdkscrollable=""  style="transform: translate3d(100%, 0px, 0px); min-height: 1px;">
               <!---->
            </div>
         </mat-tab-body>
         <!---->
      </div>
   </body>
</html>

CodePudding user response:

Try below XPath:

//input[@id=(./following::label[.='Max Driving Time_h']/@for)]

Your XPath doesn't work because it states that you need to find all input nodes if they have the same @id value as the @for value of label with text 'Max Driving Time_h' while you need only the input with corresponding label (note the . that means "context node")

CodePudding user response:

According to your sample, the following XPath //input[@id=(//label[.='Max Driving Time_h']/@for)] doesn't work since :

  • "Max Driving Time_h" text is contained inside a mat-label node, not a label one.
  • @for attribute belongs to that label node.

You can fix your XPath several ways. Don't forget to add (...)[1] to get the first result only :

(//input[@id=//mat-label[.='Max Driving Time_h']/../@for])[1]
(//input[@id=//label[./mat-label[.="Max Driving Time_h"]]/@for])[1]

That being said, to be shorter and more efficient, just use :

//input[./following::mat-label[.='Max Driving Time_h']]
  • Related