问:
Why is urql making request at wrong adress when I use server side rendering?
I am building my web application's frontend using NextJs. My client is running at http://localhost:3000/ and my graphql server is at http://localhost:5000/graphql. So I was creating Urql client and I want server side rendering. In my index.tsx I created the urql client using withUrqlClient and specified proper url for my backend:

```<code>const Index = () => {
  return (
    <div>
      <Head>
        <meta
          name="viewport"
          content="minimum-scale=1, initial-scale=1, width=device-width"
        />
      </Head>
      <Navbar />
      <h1>Hello stc</h1>
    </div>
  );
};

// create urql client
export default withUrqlClient((ssrExchange: any) => ({

  url: "http://localhost:5000/graphql",
  exchanges: [
    dedupExchange,
    cacheExchange({
      updates: {
        Mutation: {
          loginUser: (_result, _args, cache) => {
            customUpdateQuery<LoginMutation, MeQuery>(
              cache,
              { query: MeDocument },
              _result,
              (result, query) => {
                if (result.loginUser.errors) {
                  return query;
                } else {
                  return {
                    me: result.loginUser.user,
                  };
                }
              }
            );
          },
          registerUser: (_result, _args, cache) => {
            customUpdateQuery<RegisterMutation, MeQuery>(
              cache,
              { query: MeDocument },
              _result,
              (result, query) => {
                if (result.registerUser.errors) {
                  return query;
                } else {
                  return {
                    me: result.registerUser.user,
                  };
                }
              }
            );
          },
          .
          .
          .
      },
    }),
    ssrExchange,
    fetchExchange,
  ],
}))(Index);
</code>```

The problem is, when I go to /login page (or any page aside from index), and make a submit request on login form, it makes request to http://localhost:3000. I get the warning on console:

I don't think that error is in the login.tsx

Login.tsx

```<code>interface FormValues {
  usernameOrEmail: string;
  password: string;
}

// initial values for form
const initialValues: FormValues = {
  usernameOrEmail: "",
  password: "",
};

const loginSchema = yup.object().shape({
  usernameOrEmail: yup.string().required("Required"),
  password: yup.string().required("Required"),
});

const login: React.FC<loginProps> = ({}) => {
  const router = useRouter();
  const [isLoading, setIsLoading] = useState<boolean>(false);
  const [, login] = useLoginMutation();
  return (
    <div>
      <NavBar />

      <Wrapper variant="small">

        <Formik
          initialValues={initialValues}
          onSubmit={async (values: FormValues, { setErrors }) => {
            setIsLoading(true);
            // Make register mutation
            const response = await login({
              details: {
                usernameOrEmail: values.usernameOrEmail,
                password: values.password,
              },
            });
            // Handle errors
            if (response.data?.loginUser.errors) {
              setErrors(toErrorMaps(response.data.loginUser.errors));
            } else {
              // if no errors, re route to home page
              router.push("/");
            }
            setIsLoading(false);

            // Handle errors
            if (response.data?.loginUser.errors) {
              setErrors(toErrorMaps(response.data.loginUser.errors));
            } else {
              // if no errors, re route to home page
              router.push("/");
            }
          }}
          validationSchema={loginSchema}
        >
          {({ isValid, dirty }) => (
            <Form autoComplete="off">
              {/* <LinearProgress /> */}
              <FormikField
                name="usernameOrEmail"
                label="Username or Email"
                type="text"
              />

              <FormikField name="password" label="Password" type="password" />

              <Button
                variant="contained"
                color="primary"
                // disabled={!dirty||  || !isValid}
                disabled={!dirty || !isValid || isLoading}
                type="submit"
                fullWidth
              >
                Login
              </Button>
              {isLoading ? <LinearProgress color="primary" /> : <div></div>}
            </Form>
          )}
        </Formik>
      </Wrapper>
    </div>
  );
};

export default login;

Default Client: No client has been specified using urql's Provider.This means that urql will be
falling back to defaults including making requests to `/graphql`.
If that's not what you want, please create a client and add a Provider.
</code>```

Can anyone please explain whats going on ? I followed the documentation as it is: https://formidable.com/open-source/urql/docs/advanced/server-side-rendering/#nextjs

Just for reference, here's my _app.tsx

```<code>  function MyApp({ Component, pageProps }) {
  return (
    <MuiThemeProvider theme={customTheme}>
      <Component {...pageProps} />
    </MuiThemeProvider>
  );
}

export default MyApp;
</code>```

Is there a wrapper around the application that I am missing ?

答: Had the same issue and spent a lot of time without being able to solve it. I came around it by using withUrqlClient on the app component in _app.tsx which defeats the purpose and does not allow to select pages to ssr or not.

Body:
I am building my web application's frontend using NextJs. My client is running at http://localhost:3000/ and my graphql server is at http://localhost:5000/graphql. So I was creating Urql client and I want server side rendering. In my index.tsx I created the urql client using withUrqlClient and specified proper url for my backend:

const Index = () => {
  return (

        <meta
          name="viewport"
          content="minimum-scale=1, initial-scale=1, width=device-width"
        />

      <Navbar />

Hello stc

  );
};

// create urql client
export default withUrqlClient((ssrExchange: any) => ({

  url: "http://localhost:5000/graphql",
  exchanges: [
    dedupExchange,
    cacheExchange({
      updates: {
        Mutation: {
          loginUser: (_result, _args, cache) => {
            customUpdateQuery<LoginMutation, MeQuery>(
              cache,
              { query: MeDocument },
              _result,
              (result, query) => {
                if (result.loginUser.errors) {
                  return query;
                } else {
                  return {
                    me: result.loginUser.user,
                  };
                }
              }
            );
          },
          registerUser: (_result, _args, cache) => {
            customUpdateQuery<RegisterMutation, MeQuery>(
              cache,
              { query: MeDocument },
              _result,
              (result, query) => {
                if (result.registerUser.errors) {
                  return query;
                } else {
                  return {
                    me: result.registerUser.user,
                  };
                }
              }
            );
          },
          .
          .
          .
      },
    }),
    ssrExchange,
    fetchExchange,
  ],
}))(Index);

The problem is, when I go to /login page (or any page aside from index), and make a submit request on login form, it makes request to http://localhost:3000. I get the warning on console:

I don't think that error is in the login.tsx

Login.tsx

interface FormValues {
  usernameOrEmail: string;
  password: string;
}

// initial values for form
const initialValues: FormValues = {
  usernameOrEmail: "",
  password: "",
};

const loginSchema = yup.object().shape({
  usernameOrEmail: yup.string().required("Required"),
  password: yup.string().required("Required"),
});

const login: React.FC<loginProps> = ({}) => {
  const router = useRouter();
  const [isLoading, setIsLoading] = useState<boolean>(false);
  const [, login] = useLoginMutation();
  return (

      <NavBar />

      <Wrapper variant="small">

        <Formik
          initialValues={initialValues}
          onSubmit={async (values: FormValues, { setErrors }) => {
            setIsLoading(true);
            // Make register mutation
            const response = await login({
              details: {
                usernameOrEmail: values.usernameOrEmail,
                password: values.password,
              },
            });
            // Handle errors
            if (response.data?.loginUser.errors) {
              setErrors(toErrorMaps(response.data.loginUser.errors));
            } else {
              // if no errors, re route to home page
              router.push("/");
            }
            setIsLoading(false);

            // Handle errors
            if (response.data?.loginUser.errors) {
              setErrors(toErrorMaps(response.data.loginUser.errors));
            } else {
              // if no errors, re route to home page
              router.push("/");
            }
          }}
          validationSchema={loginSchema}
        >
          {({ isValid, dirty }) => (
            <Form autoComplete="off">
              {/* <LinearProgress /> */}
              <FormikField
                name="usernameOrEmail"
                label="Username or Email"
                type="text"
              />

              <FormikField name="password" label="Password" type="password" />

              <Button
                variant="contained"
                color="primary"
                // disabled={!dirty||  || !isValid}
                disabled={!dirty || !isValid || isLoading}
                type="submit"
                fullWidth
              >
                Login
              </Button>
              {isLoading ? <LinearProgress color="primary" /> :

}
            </Form>
          )}
        </Formik>
      </Wrapper>

  );
};

export default login;

Default Client: No client has been specified using urql's Provider.This means that urql will be
falling back to defaults including making requests to `/graphql`.
If that's not what you want, please create a client and add a Provider.

Can anyone please explain whats going on ? I followed the documentation as it is: https://formidable.com/open-source/urql/docs/advanced/server-side-rendering/#nextjs

Just for reference, here's my _app.tsx

  function MyApp({ Component, pageProps }) {
  return (
    <MuiThemeProvider theme={customTheme}>
      <Component {...pageProps} />
    </MuiThemeProvider>
  );
}

export default MyApp;

Is there a wrapper around the application that I am missing ?


来源: stackexchange

问:
Scrape Data i can't get
i have this issue, i need to scrape from this html data "
 Anglicare At Home Southern Region

I need to get the name of the company: "Anglicare At Home Southern Region"

From this link: https://www.agedcareguide.com.au/search/in-home-care/aus?page=1

I need to get each name of each company from that page. (I know how to create the loop after i get the name, but i just can't get the name!)

I used this code but it prints "None":

```<code>company_name = soup.find("h4", itemprop="name", class_=" tw-text-xl tw-font-bold tw-text-gray-600 tw-py-0 tw-my-0 group-hover:tw-text-link-hover")

print(company_name)
</code>```

I don't know how to get this data. Can you help?
Thank you!

答:
I highly recommend you to scrape data using requests and not Selenium. I consider
that scraping data from the HTML code is a very tedious work.

Now, if you check your Dev Tools from the web browser, you can fetch the API request that the web page is using. In your example:

So, you can copy the cURL (to Postman or https://curlconverter.com/) and convert it to Python language:

```<code>import requests
import json

headers = {
    'authority': 'www.agedcareguide.com.au',
    'sec-ch-ua': '" Not;A Brand";v="99", "Google Chrome";v="97", "Chromium";v="97"',
    'sec-ch-ua-mobile': '?0',
    'user-agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/97.0.4692.99 Safari/537.36',
    'sec-ch-ua-platform': '"Windows"',
    'accept': '*/*',
    'sec-fetch-site': 'same-origin',
    'sec-fetch-mode': 'cors',
    'sec-fetch-dest': 'empty',
    'referer': 'https://www.agedcareguide.com.au/search/in-home-care/aus?page=1',
    'accept-language': 'es-ES,es;q=0.9,en;q=0.8',
}

params = (
    ('state', 'aus'),
    ('category', 'in-home-care'),
    ('page', '1'),
)

response = requests.get('https://www.agedcareguide.com.au/api/v3/search/1/compiled-profiles', headers=headers, params=params)
json_response = json.loads(response.text)
</code>```

Finally, you can get what you want (and much more) treating the data as a JSON (or a dictionary):

```<code>data = json_response['data']
names = []

for item in data:
    names.append(item['attributes']['name'])
</code>```

ContentLicense: CC BY-SA 4.0

Title: Scrape Data i can't get

Body:
i have this issue, i need to scrape from this html data "
 Anglicare At Home Southern Region

I need to get the name of the company: "Anglicare At Home Southern Region"

From this link: https://www.agedcareguide.com.au/search/in-home-care/aus?page=1

I need to get each name of each company from that page. (I know how to create the loop after i get the name, but i just can't get the name!)

I used this code but it prints "None":

company_name = soup.find("h4", itemprop="name", class_=" tw-text-xl tw-font-bold tw-text-gray-600 tw-py-0 tw-my-0 group-hover:tw-text-link-hover")

print(company_name)

I don't know how to get this data. Can you help?
Thank you!

Body:
I highly recommend you to scrape data using requests and not Selenium. I consider
that scraping data from the HTML code is a very tedious work.

Now, if you check your Dev Tools from the web browser, you can fetch the API request that the web page is using. In your example:

So, you can copy the cURL (to Postman or https://curlconverter.com/) and convert it to Python language:

import requests
import json

headers = {
    'authority': 'www.agedcareguide.com.au',
    'sec-ch-ua': '" Not;A Brand";v="99", "Google Chrome";v="97", "Chromium";v="97"',
    'sec-ch-ua-mobile': '?0',
    'user-agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/97.0.4692.99 Safari/537.36',
    'sec-ch-ua-platform': '"Windows"',
    'accept': '*/*',
    'sec-fetch-site': 'same-origin',
    'sec-fetch-mode': 'cors',
    'sec-fetch-dest': 'empty',
    'referer': 'https://www.agedcareguide.com.au/search/in-home-care/aus?page=1',
    'accept-language': 'es-ES,es;q=0.9,en;q=0.8',
}

params = (
    ('state', 'aus'),
    ('category', 'in-home-care'),
    ('page', '1'),
)

response = requests.get('https://www.agedcareguide.com.au/api/v3/search/1/compiled-profiles', headers=headers, params=params)
json_response = json.loads(response.text)

Finally, you can get what you want (and much more) treating the data as a JSON (or a dictionary):

data = json_response['data']
names = []

for item in data:
    names.append(item['attributes']['name'])


问:
Puppeteer chrome get active/visible tab
In a chrome extension you can use below to find the active tab in a window

```<code>chrome.tabs.query({
            currentWindow: true,
            active: true,
        }
</code>```

I have a below code which connects to existing browser and get all the pages. I am not able to make out if there is a way for me to know which tab/page is currently the active one and get its url (page.url(), but which one from the the array to use?)

```<code>const puppeteer = require('puppeteer');

debuggerUrl = "http://127.0.0.1:9999/json/version"

const request = require('request');

request(debuggerUrl, function (error, response, body) {
  data = JSON.parse(body);
  webSocketDebuggerUrl = data["webSocketDebuggerUrl"];
  console.log("Connecting to ", webSocketDebuggerUrl);
  puppeteer.connect({browserWSEndpoint: webSocketDebuggerUrl}).then(async browser => {
    var pages = await browser.pages();
    console.log(pages);
    console.log(await browser.targets())
    await browser.disconnect();
  })
});
</code>```

答:
```<code>    const pages = await browser.pages();
    const vis_results = await Promise.all(pages.map(async (p) => {
        const state = await p.evaluate(() => document.webkitHidden);
        return !state;
    }));
    let visiblePage = pages.filter((_v, index) => vis_results[index])[0];
</code>```

Title: Puppeteer chrome get active/visible tab

Body:
In a chrome extension you can use below to find the active tab in a window

chrome.tabs.query({
            currentWindow: true,
            active: true,
        }

I have a below code which connects to existing browser and get all the pages. I am not able to make out if there is a way for me to know which tab/page is currently the active one and get its url (page.url(), but which one from the the array to use?)

const puppeteer = require('puppeteer');

debuggerUrl = "http://127.0.0.1:9999/json/version"

const request = require('request');

request(debuggerUrl, function (error, response, body) {
  data = JSON.parse(body);
  webSocketDebuggerUrl = data["webSocketDebuggerUrl"];
  console.log("Connecting to ", webSocketDebuggerUrl);
  puppeteer.connect({browserWSEndpoint: webSocketDebuggerUrl}).then(async browser => {
    var pages = await browser.pages();
    console.log(pages);
    console.log(await browser.targets())
    await browser.disconnect();
  })
});


问:
How to move an Outlook attachment to a vb.net Winforms app?
I've got a user who wants to be able to drag an attachment from Outlook to a vb.net Winforms application.  How do I do this?

I found this link: https://www.codeproject.com/Articles/7140/Drag-and-Drop-Attached-File-From-Outlook-97-and-ab, but some of the examples seem to be missing plus it's in C#.

I'm also concerned since we're using a legacy app written in Visual Studio 2012 with .net 4.6.1 (this can't be changed to do licensing and such).

Can someone give me someplace to get started?

** Update - 2/21/22 **

I put together code based on the website referenced above and the sample code.  The sample code did not work, but it helped me fill in the blanks from the website.  I now have the issue that dragging an attachment to the Winform gives me ALL the attachments.  The code takes the e-mail, loops through all the attachments, and processes them all.  Is there anyway to get just the attachment that is dragged over?

Here is the code on the form DragDrop event:

```<code>  Private Sub frmPurchaseOrder_DragDrop(sender As Object, e As DragEventArgs) Handles MyBase.DragDrop
        lstFiles.ClearFiles()
        Try
            If e.Data.GetDataPresent("FileGroupDescriptor") Then
                Dim explorer As Explorer = mobjApplication.ActiveExplorer()
                If explorer.AttachmentSelection.Count > 0 Then
                    Dim i As Integer = 0
                    For Each objAttachment As Attachment In explorer.AttachmentSelection
                        If objAttachment IsNot Nothing Then
                            lstFiles.AddFile("attachment #" + i.ToString())
                            lstFiles.AddFile("File Name: " + objAttachment.FileName)
                            Dim strFile As String = Path.Combine("c:\temp", FixFileName(objAttachment.FileName))
                            objAttachment.SaveAsFile(strFile)
                            Marshal.ReleaseComObject(objAttachment)
                            i += 1
                        End If
                    Next
                Else
                    'supports a drop of a Outlook message
                    For Each objMi As MailItem In mobjApplication.ActiveExplorer.Selection()
                        'hardcode a destination path for testing
                        Dim strFile As String = Path.Combine("c:\temp", FixFileName(objMi.Subject + ".msg"))
                        'lstFiles.AddFile(strFile)
                        objMi.SaveAs(strFile)
                        GetAttachmentsInfo(objMi)
                    Next
                End If
            End If

        Catch ex As System.Exception
            'lstFiles.Items.Add("An error occured in the drop event")
            'lstFiles.Items.Add(ex.ToString)
            MessageBox.Show("Error adding file: " & ex.ToString, "Error adding file")
        End Try
    End Sub
</code>```

答:
Nothing really has been changed so far. You are referring to the valid article with sample code which can be used nowadays. Take a look at the https://github.com/tonyfederer/OutlookFileDrag sample code.

If you need to get VB.NET code instead of C# there are multiple converters on the web. But I'd suggest converting the code manually.

Body:
I've got a user who wants to be able to drag an attachment from Outlook to a vb.net Winforms application.  How do I do this?

I found this link: https://www.codeproject.com/Articles/7140/Drag-and-Drop-Attached-File-From-Outlook-97-and-ab, but some of the examples seem to be missing plus it's in C#.

I'm also concerned since we're using a legacy app written in Visual Studio 2012 with .net 4.6.1 (this can't be changed to do licensing and such).

Can someone give me someplace to get started?

** Update - 2/21/22 **

I put together code based on the website referenced above and the sample code.  The sample code did not work, but it helped me fill in the blanks from the website.  I now have the issue that dragging an attachment to the Winform gives me ALL the attachments.  The code takes the e-mail, loops through all the attachments, and processes them all.  Is there anyway to get just the attachment that is dragged over?

Here is the code on the form DragDrop event:

  Private Sub frmPurchaseOrder_DragDrop(sender As Object, e As DragEventArgs) Handles MyBase.DragDrop
        lstFiles.ClearFiles()
        Try
            If e.Data.GetDataPresent("FileGroupDescriptor") Then
                Dim explorer As Explorer = mobjApplication.ActiveExplorer()
                If explorer.AttachmentSelection.Count > 0 Then
                    Dim i As Integer = 0
                    For Each objAttachment As Attachment In explorer.AttachmentSelection
                        If objAttachment IsNot Nothing Then
                            lstFiles.AddFile("attachment #" + i.ToString())
                            lstFiles.AddFile("File Name: " + objAttachment.FileName)
                            Dim strFile As String = Path.Combine("c:\temp", FixFileName(objAttachment.FileName))
                            objAttachment.SaveAsFile(strFile)
                            Marshal.ReleaseComObject(objAttachment)
                            i += 1
                        End If
                    Next
                Else
                    'supports a drop of a Outlook message
                    For Each objMi As MailItem In mobjApplication.ActiveExplorer.Selection()
                        'hardcode a destination path for testing
                        Dim strFile As String = Path.Combine("c:\temp", FixFileName(objMi.Subject + ".msg"))
                        'lstFiles.AddFile(strFile)
                        objMi.SaveAs(strFile)
                        GetAttachmentsInfo(objMi)
                    Next
                End If
            End If

        Catch ex As System.Exception
            'lstFiles.Items.Add("An error occured in the drop event")
            'lstFiles.Items.Add(ex.ToString)
            MessageBox.Show("Error adding file: " & ex.ToString, "Error adding file")
        End Try
    End Sub


问:
Conflict between Antitypical Result and Alamofire Result
I have the following Swift function in a protocol that represents a POST HTTP request:

```<code>func post<T: Mappable>(url: NSURL, parameters: [String: AnyObject]?, completion: ((Result<T, APIClientError>) -> ())?)
</code>```

In this case, I'm doing import Result to get Result from Antitypical, because I don't want this protocol to depend on Alamofire.

In an implementation of this protocol, I want to use Alamofire to do the actual HTTP request:

```<code>func post<T: Mappable>(url: NSURL, parameters: [String: AnyObject]?, completion: (Result<T, APIClientError> -> ())? = nil) {
    Alamofire.request(.POST, url.URLString, parameters: parameters, encoding: .JSON)
        .validate()
</code>```

The problem is that there is a conflict between Antitypical's Result and Alamofire's Result:

```<code>AlamofireHTTPClient.swift:21:87: 'Result' is ambiguous for type lookup in this context
</code>```

How can I specify that I want to use Result from Antitypical? Or if you know a better way to solve the problem?

答:
Swift 5

In Swift 5, you can specify the Swift result type as:

```<code>Swift.Result<T, APIClientError>
</code>```

Alamofire can be done as:

```<code>Alamofire.Result<Data>
</code>```

ContentLicense: CC BY-SA 3.0

Body:
I have the following Swift function in a protocol that represents a POST HTTP request:

func post<T: Mappable>(url: NSURL, parameters: [String: AnyObject]?, completion: ((Result<T, APIClientError>) -> ())?)

In this case, I'm doing import Result to get Result from Antitypical, because I don't want this protocol to depend on Alamofire.

In an implementation of this protocol, I want to use Alamofire to do the actual HTTP request:

func post<T: Mappable>(url: NSURL, parameters: [String: AnyObject]?, completion: (Result<T, APIClientError> -> ())? = nil) {
    Alamofire.request(.POST, url.URLString, parameters: parameters, encoding: .JSON)
        .validate()

The problem is that there is a conflict between Antitypical's Result and Alamofire's Result:

AlamofireHTTPClient.swift:21:87: 'Result' is ambiguous for type lookup in this context

How can I specify that I want to use Result from Antitypical? Or if you know a better way to solve the problem?

Body:
Swift 5

In Swift 5, you can specify the Swift result type as:

Swift.Result<T, APIClientError>

Alamofire can be done as:

Alamofire.Result<Data>


问:
How to sign a Solana Raydium swap?
I am getting a NotEnoughSigners error using amm_instruction::swap_base_in() for Raydium swap in Solana (https://github.com/raydium-io/raydium-contract-instructions). What am I doing wrong here? As far as I can tell, one signer is required and one is being submitted, but I get a NotEnoughSigners error.</p>
```<code>// pubkey
use std::{str::FromStr};
use solana_program::{pubkey, pubkey::Pubkey};

// rpc
use solana_client::rpc_client::RpcClient;

mod amm_instruction;

fn main() {
    // pool info
    let program_id: Pubkey = pubkey!("675kPX9MHTjS2zt1qfr1NYHuzeLXfQM9H24wFSUt1Mp8");
    let amm_id: Pubkey = pubkey!("58oQChx4yWmvKdwLLZzBi4ChoCc2fqCUWBkwMihLYQo2");
    let amm_authority: Pubkey = pubkey!("5Q544fKrFoe6tsEbD7S8EmxGTJYAKtTVhAW5Q5pge4j1");
    let amm_open_orders: Pubkey = pubkey!("HRk9CMrpq7Jn9sh7mzxE8CChHG8dneX9p475QKz4Fsfc");
    let amm_target_orders: Pubkey = pubkey!("CZza3Ej4Mc58MnxWA385itCC9jCo3L1D7zc3LKy1bZMR");
    let pool_coin_token_account: Pubkey = pubkey!("DQyrAcCrDXQ7NeoqGgDCZwBvWDcYmFCjSb9JtteuvPpz");
    let pool_pc_token_account: Pubkey = pubkey!("HLmqeL62xR1QoZ1HKKbXRrdN1p3phKpxRMb2VVopvBBz");
    let serum_program_id: Pubkey = pubkey!("9xQeWvG816bUx9EPjHmaT23yvVM2ZWbrrpZb9PusVFin");
    let serum_market: Pubkey = pubkey!("9wFFyRfZBsuAha4YcuxcXLKwMxJR43S7fPfQLusDBzvT");
    let serum_bids: Pubkey = pubkey!("14ivtgssEBoBjuZJtSAPKYgpUK7DmnSwuPMqJoVTSgKJ");
    let serum_asks: Pubkey = pubkey!("CEQdAFKdycHugujQg9k2wbmxjcpdYZyVLfV9WerTnafJ");
    let serum_event_queue: Pubkey = pubkey!("5KKsLVU6TcbVDK4BS6K1DGDxnh4Q9xjYJ8XaDCG5t8ht");
    let serum_coin_vault_account: Pubkey = pubkey!("36c6YqAwyGKQG66XEp2dJc5JqjaBNv7sVghEtJv4c7u6");
    let serum_pc_vault_account: Pubkey = pubkey!("8CFo8bL8mZQK8abbFyypFMwEDd8tVJjHTTojMLgQTUSZ");
    let serum_vault_signer: Pubkey = pubkey!("F8Vyqk3unwxkXukZFQeYyGmFfTG3CAX4v24iyrjEYBJV");
    let uer_source_token_account: Pubkey = pubkey!("AgzZJAiniqwX4MAkf7KGuza4oYk5XNBHUZ4XZeca7osC");
    let uer_destination_token_account: Pubkey = pubkey!("ENJH5ho47pbHmMcoerGtRywQpkcbtWtnCfsKdHesf5E5");
    let user_source_owner: Pubkey = pubkey!("FBH3xoEVNF85pkmpfsgevyTW9ewtL2M1xuHzJwaxdLm5");
    let amount_in: u64 = 1_000_000;
    let minimum_amount_out: u64 = 10_321_182;

    // connect to cluster
    //let url = "https://api.mainnet-beta.solana.com".to_string();
    let url = "https://api.devnet.solana.com".to_string();
    let rpc_client = RpcClient::new(url);

    let latest_blockhash = rpc_client.get_latest_blockhash().unwrap();
    let alice = solana_sdk::signer::keypair::read_keypair_file("/Users/Me/.config/solana/id.json").unwrap();

    let swap_instructions = amm_instruction::swap_base_in(
        &program_id,
        &amm_id,
        &amm_authority,
        &amm_open_orders,
        &amm_target_orders,
        &pool_coin_token_account,
        &pool_pc_token_account,
        &serum_program_id,
        &serum_market,
        &serum_bids,
        &serum_asks,
        &serum_event_queue,
        &serum_coin_vault_account,
        &serum_pc_vault_account,
        &serum_vault_signer,
        &uer_source_token_account,
        &uer_destination_token_account,
        &user_source_owner,
        amount_in,
        minimum_amount_out
    ).unwrap();

    let payer: Option<Pubkey> = Some(solana_program::pubkey::Pubkey::from_str("5C8rbEJUuLR2nTkEqiyjzmyBtxAiseS2Aoq7YU3c8cgL").unwrap());

    let tx = solana_sdk::transaction::Transaction::new_signed_with_payer(&[swap_instructions], payer.as_ref(), &[&alice], latest_blockhash);

    let signature = rpc_client.send_and_confirm_transaction(&tx);

    println!("swap: {:?}",signature);
}
</code>```

答:
If you look at the code that you linked, you'll see that this instruction expects only one signature from user_source_owner: https://github.com/raydium-io/raydium-contract-instructions/blob/cbd7affe245166f7baceb7e68d123220e0fcd331/amm_instruction.rs#L594

This means that your transaction must be declared as:

```<code>let payer = Keypair::from_bytes(<INSERT_BYTES_HERE>); // this must be a some Signer in order to be declared as a payer, so use whichever method you need to get that keypair
let user_source_owner = Keypair::form_bytes(<PUT_BYTES_HERE>); // same here
let tx = solana_sdk::transaction::Transaction::new_signed_with_payer(&[swap_instructions], Some(&payer.pubkey()), &[&payer, &user_source_owner], latest_blockhash);
</code>```

Title: How to sign a Solana Raydium swap?

Body:
I am getting a NotEnoughSigners error using amm_instruction::swap_base_in() for Raydium swap in Solana (https://github.com/raydium-io/raydium-contract-instructions). What am I doing wrong here? As far as I can tell, one signer is required and one is being submitted, but I get a NotEnoughSigners error.

// pubkey
use std::{str::FromStr};
use solana_program::{pubkey, pubkey::Pubkey};

// rpc
use solana_client::rpc_client::RpcClient;

mod amm_instruction;

fn main() {
    // pool info
    let program_id: Pubkey = pubkey!("675kPX9MHTjS2zt1qfr1NYHuzeLXfQM9H24wFSUt1Mp8");
    let amm_id: Pubkey = pubkey!("58oQChx4yWmvKdwLLZzBi4ChoCc2fqCUWBkwMihLYQo2");
    let amm_authority: Pubkey = pubkey!("5Q544fKrFoe6tsEbD7S8EmxGTJYAKtTVhAW5Q5pge4j1");
    let amm_open_orders: Pubkey = pubkey!("HRk9CMrpq7Jn9sh7mzxE8CChHG8dneX9p475QKz4Fsfc");
    let amm_target_orders: Pubkey = pubkey!("CZza3Ej4Mc58MnxWA385itCC9jCo3L1D7zc3LKy1bZMR");
    let pool_coin_token_account: Pubkey = pubkey!("DQyrAcCrDXQ7NeoqGgDCZwBvWDcYmFCjSb9JtteuvPpz");
    let pool_pc_token_account: Pubkey = pubkey!("HLmqeL62xR1QoZ1HKKbXRrdN1p3phKpxRMb2VVopvBBz");
    let serum_program_id: Pubkey = pubkey!("9xQeWvG816bUx9EPjHmaT23yvVM2ZWbrrpZb9PusVFin");
    let serum_market: Pubkey = pubkey!("9wFFyRfZBsuAha4YcuxcXLKwMxJR43S7fPfQLusDBzvT");
    let serum_bids: Pubkey = pubkey!("14ivtgssEBoBjuZJtSAPKYgpUK7DmnSwuPMqJoVTSgKJ");
    let serum_asks: Pubkey = pubkey!("CEQdAFKdycHugujQg9k2wbmxjcpdYZyVLfV9WerTnafJ");
    let serum_event_queue: Pubkey = pubkey!("5KKsLVU6TcbVDK4BS6K1DGDxnh4Q9xjYJ8XaDCG5t8ht");
    let serum_coin_vault_account: Pubkey = pubkey!("36c6YqAwyGKQG66XEp2dJc5JqjaBNv7sVghEtJv4c7u6");
    let serum_pc_vault_account: Pubkey = pubkey!("8CFo8bL8mZQK8abbFyypFMwEDd8tVJjHTTojMLgQTUSZ");
    let serum_vault_signer: Pubkey = pubkey!("F8Vyqk3unwxkXukZFQeYyGmFfTG3CAX4v24iyrjEYBJV");
    let uer_source_token_account: Pubkey = pubkey!("AgzZJAiniqwX4MAkf7KGuza4oYk5XNBHUZ4XZeca7osC");
    let uer_destination_token_account: Pubkey = pubkey!("ENJH5ho47pbHmMcoerGtRywQpkcbtWtnCfsKdHesf5E5");
    let user_source_owner: Pubkey = pubkey!("FBH3xoEVNF85pkmpfsgevyTW9ewtL2M1xuHzJwaxdLm5");
    let amount_in: u64 = 1_000_000;
    let minimum_amount_out: u64 = 10_321_182;

    // connect to cluster
    //let url = "https://api.mainnet-beta.solana.com".to_string();
    let url = "https://api.devnet.solana.com".to_string();
    let rpc_client = RpcClient::new(url);

    let latest_blockhash = rpc_client.get_latest_blockhash().unwrap();
    let alice = solana_sdk::signer::keypair::read_keypair_file("/Users/Me/.config/solana/id.json").unwrap();

    let swap_instructions = amm_instruction::swap_base_in(
        &program_id,
        &amm_id,
        &amm_authority,
        &amm_open_orders,
        &amm_target_orders,
        &pool_coin_token_account,
        &pool_pc_token_account,
        &serum_program_id,
        &serum_market,
        &serum_bids,
        &serum_asks,
        &serum_event_queue,
        &serum_coin_vault_account,
        &serum_pc_vault_account,
        &serum_vault_signer,
        &uer_source_token_account,
        &uer_destination_token_account,
        &user_source_owner,
        amount_in,
        minimum_amount_out
    ).unwrap();

    let payer: Option<Pubkey> = Some(solana_program::pubkey::Pubkey::from_str("5C8rbEJUuLR2nTkEqiyjzmyBtxAiseS2Aoq7YU3c8cgL").unwrap());

    let tx = solana_sdk::transaction::Transaction::new_signed_with_payer(&[swap_instructions], payer.as_ref(), &[&alice], latest_blockhash);

    let signature = rpc_client.send_and_confirm_transaction(&tx);

    println!("swap: {:?}",signature);
}

Body:
If you look at the code that you linked, you'll see that this instruction expects only one signature from user_source_owner: https://github.com/raydium-io/raydium-contract-instructions/blob/cbd7affe245166f7baceb7e68d123220e0fcd331/amm_instruction.rs#L594

This means that your transaction must be declared as:

let payer = Keypair::from_bytes(<INSERT_BYTES_HERE>); // this must be a some Signer in order to be declared as a payer, so use whichever method you need to get that keypair
let user_source_owner = Keypair::form_bytes(<PUT_BYTES_HERE>); // same here
let tx = solana_sdk::transaction::Transaction::new_signed_with_payer(&[swap_instructions], Some(&payer.pubkey()), &[&payer, &user_source_owner], latest_blockhash);


问:
Trigger URL WebApp every specific Time
I want to trigger URL opened in new tab every 10 minutes I tried with this function

```<code>function openTab() {

var url = 'https://script.google.com/macros/s/...................../exec';

var html = "<script>window.open('" + url + "');google.script.host.close();</script>";

var userInterface = HtmlService.createHtmlOutput(html);

SpreadsheetApp.getUi().showModalDialog(userInterface, 'Open Tab');

}
</code>```

but it can't be triggered on simple trigger or installable trigger

I searched a lot but i'm not sure to execute this

答:
Time-Driven triggers can't open dialogs and sidebars, the alternative is to first open a sidebar to put in it client-side code that will open the dialog.

Related

Run script timerbased clientside [GAS]

Google Sheets custom sidebar: How to display a current cell value in sidebar without reload the sidebar?

Title: Trigger URL WebApp every specific Time

Body:
I want to trigger URL opened in new tab every 10 minutes I tried with this function

function openTab() {

var url = 'https://script.google.com/macros/s/...................../exec';

var html = "";

var userInterface = HtmlService.createHtmlOutput(html);

SpreadsheetApp.getUi().showModalDialog(userInterface, 'Open Tab');

}

but it can't be triggered on simple trigger or installable trigger

I searched a lot but i'm not sure to execute this


问:
open a textfile and remove redundant lines and characters
I have a textfile containing words, characters, numbers, and empty lines  as below:

```<code>This is an example /
The Date is: 07 Feb 2022
2.03 4.0 5.0 2*6 3*4
9e-2 7.0 2 6 2*3 5.0 /
</code>```

I want to only keep those lines with numbers, and delete / anywhere in the file. Also I want to change those numbers next to the * in such a way that:

2*6 becomes 6 6

3*4 becomes 4 4 4

2*3 becomes 3 3

And finally have such a file

```<code>2.03 4.0 5.0 6.0 6.0 4.0 4.0 4.0
9e-2 7.0 2.0 6.0 3.0 3.0 5.0
</code>```

I have written a code to do these, but the run time is high and I think it is not a good way to do that.

I initially opened the textfile and removed the / and saved that file as target1

```<code>import os
import time
start = time.time()

with open('Ptest1.txt, 'r') as infile1, open('target1.txt', 'w') as outfile1:
    A = infile1.read()
    B = A.replace("/", "")
    outfile1.write(B)
</code>```

Then, I opened it again and this time I removed the lines holding letters and empty lines using this code, and saved it as target2:

```<code>keep_these = []
def is_valid(t):
    try:
        float(t.replace('*', '0'))
        return True
    except ValueError:
        pass
    return False

with open('target1.txt', encoding='utf-8') as infile2, open('target2.txt', 'w') as outfile2:
    for line in infile2:
        if all(is_valid(t) for t in line.strip().split()):
            keep_these.append(line)
            if line.strip():
                outfile2.write(line)

os.remove('target1.txt')
</code>```

Finally, I used this code below to expand the numbers at the sides of *

```<code>T = open('target2.txt', 'r')

def expand(a):
    import numpy as np
    b = a.readlines()
    c = [x.replace('\n','') for x in b]
    d = [j for i in c for j in i.split()]
    e=[]
    for i in d:
        if "*" in i:
            a=[i.split("*")[1]]*int(i.split("*")[0])
            e.extend(a)
        else:
            e.append(i)
    f = np.array(e)
    g = [float(numeric_string) for numeric_string in f]
    h = np.array(g)
    return h

MM = expand(T)

end = time.time()
print(f"Runtime of the program is {end - start}")
</code>```

答:
Here is what I tried:

```<code>import os
import time
import string

start = time.time()
def expand(chunk):

    l = chunk.split("*")
    chunk = [str(float(l[1]))] * int(l[0])

    return chunk

with open('/path/to/Test.txt', 'r') as infile1, open('target1.txt', 'w') as outfile1:
    for line in infile1:
        if set(string.ascii_letters.replace("e","")) & set(line):
            continue

        chunks = line.split(" ")
        #Get rid of newlines
        chunks = list(map(lambda chunk: chunk.strip(), chunks))
        if "/" in chunks:
            chunks.remove("/")

        new_chunks = []
        for i in range(len(chunks)):
            if '*' in chunks[i]:
                new_chunks += expand(chunks[i])
            else:
                new_chunks.append(chunks[i])
        new_chunks[len(new_chunks)-1] = new_chunks[len(new_chunks)-1]+"\n"
        new_line = " ".join(new_chunks)
        outfile1.write(new_line)

end = time.time()
print(f"Runtime of the program is {end - start}")
</code>```

I timed both your program and my program using the text file provided in the comments and I got:

```<code>Runtime of the program is 1.3493189811706543
</code>```

for mine and

```<code>Runtime of the program is 4.36532998085022
</code>```

for yours. Checking the differences, there are about four more lines out of some 71k lines produced by my code in comparison to your code, so I think the results do not deviate too much.

One issue I noticed is that the results of MM are not written to the file at the end. Anyways, let me know if this code above leads to faster processing.

Body:
I have a textfile containing words, characters, numbers, and empty lines  as below:

This is an example /
The Date is: 07 Feb 2022
2.03 4.0 5.0 2*6 3*4
9e-2 7.0 2 6 2*3 5.0 /

I want to only keep those lines with numbers, and delete / anywhere in the file. Also I want to change those numbers next to the * in such a way that:

2*6 becomes 6 6

3*4 becomes 4 4 4

2*3 becomes 3 3

And finally have such a file

2.03 4.0 5.0 6.0 6.0 4.0 4.0 4.0
9e-2 7.0 2.0 6.0 3.0 3.0 5.0

I have written a code to do these, but the run time is high and I think it is not a good way to do that.

I initially opened the textfile and removed the / and saved that file as target1

import os
import time
start = time.time()

with open('Ptest1.txt, 'r') as infile1, open('target1.txt', 'w') as outfile1:
    A = infile1.read()
    B = A.replace("/", "")
    outfile1.write(B)

Then, I opened it again and this time I removed the lines holding letters and empty lines using this code, and saved it as target2:

keep_these = []
def is_valid(t):
    try:
        float(t.replace('*', '0'))
        return True
    except ValueError:
        pass
    return False

with open('target1.txt', encoding='utf-8') as infile2, open('target2.txt', 'w') as outfile2:
    for line in infile2:
        if all(is_valid(t) for t in line.strip().split()):
            keep_these.append(line)
            if line.strip():
                outfile2.write(line)

os.remove('target1.txt')

Finally, I used this code below to expand the numbers at the sides of *

T = open('target2.txt', 'r')

def expand(a):
    import numpy as np
    b = a.readlines()
    c = [x.replace('\n','') for x in b]
    d = [j for i in c for j in i.split()]
    e=[]
    for i in d:
        if "*" in i:
            a=[i.split("*")[1]]*int(i.split("*")[0])
            e.extend(a)
        else:
            e.append(i)
    f = np.array(e)
    g = [float(numeric_string) for numeric_string in f]
    h = np.array(g)
    return h

MM = expand(T)

end = time.time()
print(f"Runtime of the program is {end - start}")

Body:
Here is what I tried:

import os
import time
import string

start = time.time()
def expand(chunk):

    l = chunk.split("*")
    chunk = [str(float(l[1]))] * int(l[0])

    return chunk

with open('/path/to/Test.txt', 'r') as infile1, open('target1.txt', 'w') as outfile1:
    for line in infile1:
        if set(string.ascii_letters.replace("e","")) & set(line):
            continue

        chunks = line.split(" ")
        #Get rid of newlines
        chunks = list(map(lambda chunk: chunk.strip(), chunks))
        if "/" in chunks:
            chunks.remove("/")

        new_chunks = []
        for i in range(len(chunks)):
            if '*' in chunks[i]:
                new_chunks += expand(chunks[i])
            else:
                new_chunks.append(chunks[i])
        new_chunks[len(new_chunks)-1] = new_chunks[len(new_chunks)-1]+"\n"
        new_line = " ".join(new_chunks)
        outfile1.write(new_line)

end = time.time()
print(f"Runtime of the program is {end - start}")

I timed both your program and my program using the text file provided in the comments and I got:

Runtime of the program is 1.3493189811706543

for mine and

Runtime of the program is 4.36532998085022

for yours. Checking the differences, there are about four more lines out of some 71k lines produced by my code in comparison to your code, so I think the results do not deviate too much.

One issue I noticed is that the results of MM are not written to the file at the end. Anyways, let me know if this code above leads to faster processing.


问:
move_upload_file, return false but still working and not moving correctlly
I am sending image from android apps to server. The problem is image not moving to the correct path, but only at current directory (only in which that php script stored). I tested this codes on local server and webserver, getting same result. Any one can find out whats problems.

Local Server:  XAMPP 1.7.7

My PHP Script :

```<code><?php
    $base=$_REQUEST['image'];
    $Username=$_REQUEST['Username'];
    $binary=base64_decode($base);
    header('Content-Type: bitmap; charset=utf-8');

    $file = fopen($Username.'.png', 'w');
    fwrite($file, $binary);

    $uploadFilename = '/htdocs/android/ProfileImage/';

    $tr =move_uploaded_file($_FILES[$file]['tmp_name'], $uploadFilename);
    if($tr)
   echo 'true';
    else
   echo 'false';
 echo 'Successfully Uploaded';
   ?>
</code>```

Showing Output and Error in Local Server

Strict Standards: Resource ID#3 used as offset, casting to integer (3) in C:\xampp\htdocs\android\uploadSimage.php on line 12

Notice: Undefined offset: 3 in C:\xampp\htdocs\android\uploadSimage.php on line 12

falseSuccessfully Uploaded

Showing Output and Error in Webserver

Notice: Undefined offset: 3 in C:...\uploadSimage.php on line 12

falseSuccessfully Uploaded

答:
If you're using XAMPP:</p>
```<code>sudo chmod 777 -R /opt/lampp/htdocs/
</code>```

Body:
I am sending image from android apps to server. The problem is image not moving to the correct path, but only at current directory (only in which that php script stored). I tested this codes on local server and webserver, getting same result. Any one can find out whats problems.

Local Server:  XAMPP 1.7.7

My PHP Script :

<?php
    $base=$_REQUEST['image'];
    $Username=$_REQUEST['Username'];
    $binary=base64_decode($base);
    header('Content-Type: bitmap; charset=utf-8');

    $file = fopen($Username.'.png', 'w');
    fwrite($file, $binary);

    $uploadFilename = '/htdocs/android/ProfileImage/';

    $tr =move_uploaded_file($_FILES[$file]['tmp_name'], $uploadFilename);
    if($tr)
   echo 'true';
    else
   echo 'false';
 echo 'Successfully Uploaded';
   ?>

Showing Output and Error in Local Server

Strict Standards: Resource ID#3 used as offset, casting to integer (3) in C:\xampp\htdocs\android\uploadSimage.php on line 12

Notice: Undefined offset: 3 in C:\xampp\htdocs\android\uploadSimage.php on line 12

falseSuccessfully Uploaded

Showing Output and Error in Webserver

Notice: Undefined offset: 3 in C:...\uploadSimage.php on line 12

falseSuccessfully Uploaded

Body:
If you're using XAMPP:

sudo chmod 777 -R /opt/lampp/htdocs/


问:
Extension's script does not wait for whole page to load before running
I've recently started working on a chrome extension which has to wait for a YouTube page to load before adding a button at a certain place in the already existing code.

I've used getElementById() to get the element, but most of the time my page doesn't have time to fully load that the script already finished.

I've checked many topics regarding this issue and stumbled across window.addEventListener('load', submitAction); which doesn't actually waits for the whole page to load, or at least it doesn't look like it. When I try to print the output of the getElementById()'s output, the result is null.

I've been trying to use other kind of event listeners, using it on document and not on window, trying to wait for  DOMContentLoaded as it looks like it's also waiting for the document to fully load but nothing actually waits for the whole page to load.

The most optimal thing I would like to do would be that the page loads, when the element I am looking for loads, I simply grab it, create a button, append it and it seamlessly appears in the page without any latency.

Am I doing something wrong here?*

Here's a sample of my code :

manifest.json :

```<code>{
    "name": "Name",
    "description": "Description.",
    "version": "1.0",
    "manifest_version": 2,
    "permissions": [
      "activeTab"
    ],
    "content_scripts": [
      {
        "matches": ["https://*.youtube.com/c/*"],
        "js": ["content-script.js"],
        "run_at": "document_idle"
      }
    ],
    "background": {
      "scripts": ["background.js"],
      "persistent": false
    }
}
</code>```

background.js :

```<code>chrome.tabs.onUpdated.addListener( function (tabId, changeInfo, tab) {
  if (changeInfo.status == 'complete') {
    window.onload = function() {
      chrome.tabs.executeScript({
        file: "content-script.js"
      });
    }
  }
})
</code>```

content-script.js :

```<code>window.addEventListener('load', submitAction);

function submitAction()
{
  var youtubeName = document.getElementById("channel-name")

  console.log("========================")
  console.log(youtubeName)
  console.log("========================")
}
</code>```

答:
Attaching your code to the document-idle, which is the latest run-at value, will fire immediately after window.load event fires:

The browser chooses a time to inject scripts between "document_end" and immediately after the window.onload event fires

source

If the DOM gets hydrated (or mutated) with elements post load, like what seemingly happens on Youtube, then the element will not exist at the time of that event firing.

I would suggest using a different method, like a mutation observer, rather than a traditional event listener.

Example:

const callback = function(mutationsList, observer) {
    for (const mutation of mutationsList) {
        if (mutation.target.id === "channel-name") {
            console.log("Element found:", document.getElementById("channel-name"));
            // disconnect the observer
            observer.disconnect();
            // element exists, run your code below
        }
    }
};
const observer = new MutationObserver(callback);
observer.observe(document.body, {childList: true, subtree: true });
```

The snippet above watches the dom for mutations and when a mutation occurs that has a target with the id of channel-name, it executes code. In the example above, I disconnect the observer (which you may or may not want to do) and then I log the element.

Body:
I've recently started working on a chrome extension which has to wait for a YouTube page to load before adding a button at a certain place in the already existing code.

I've used getElementById() to get the element, but most of the time my page doesn't have time to fully load that the script already finished.

I've checked many topics regarding this issue and stumbled across window.addEventListener('load', submitAction); which doesn't actually waits for the whole page to load, or at least it doesn't look like it. When I try to print the output of the getElementById()'s output, the result is null.

I've been trying to use other kind of event listeners, using it on document and not on window, trying to wait for  DOMContentLoaded as it looks like it's also waiting for the document to fully load but nothing actually waits for the whole page to load.

The most optimal thing I would like to do would be that the page loads, when the element I am looking for loads, I simply grab it, create a button, append it and it seamlessly appears in the page without any latency.

Am I doing something wrong here?*

Here's a sample of my code :

manifest.json :

{
    "name": "Name",
    "description": "Description.",
    "version": "1.0",
    "manifest_version": 2,
    "permissions": [
      "activeTab"
    ],
    "content_scripts": [
      {
        "matches": ["https://*.youtube.com/c/*"],
        "js": ["content-script.js"],
        "run_at": "document_idle"
      }
    ],
    "background": {
      "scripts": ["background.js"],
      "persistent": false
    }
}

background.js :

chrome.tabs.onUpdated.addListener( function (tabId, changeInfo, tab) {
  if (changeInfo.status == 'complete') {
    window.onload = function() {
      chrome.tabs.executeScript({
        file: "content-script.js"
      });
    }
  }
})

content-script.js :

window.addEventListener('load', submitAction);

function submitAction()
{
  var youtubeName = document.getElementById("channel-name")

  console.log("========================")
  console.log(youtubeName)
  console.log("========================")
}

Body:
Attaching your code to the document-idle, which is the latest run-at value, will fire immediately after window.load event fires:

The browser chooses a time to inject scripts between "document_end" and immediately after the window.onload event fires

source

If the DOM gets hydrated (or mutated) with elements post load, like what seemingly happens on Youtube, then the element will not exist at the time of that event firing.

I would suggest using a different method, like a mutation observer, rather than a traditional event listener.

Example:

const callback = function(mutationsList, observer) {
    for (const mutation of mutationsList) {
        if (mutation.target.id === "channel-name") {
            console.log("Element found:", document.getElementById("channel-name"));
            // disconnect the observer
            observer.disconnect();
            // element exists, run your code below
        }
    }
};
const observer = new MutationObserver(callback);
observer.observe(document.body, {childList: true, subtree: true });

The snippet above watches the dom for mutations and when a mutation occurs that has a target with the id of channel-name, it executes code. In the example above, I disconnect the observer (which you may or may not want to do) and then I log the element.


问:
Printing using JS and @media print CSS but content pushed down
My content in the print preview window is displaying down about 5 or 6 lines.

Since I've already dealt with height, margin & padding, I'm unsure what's keeping it down.  I can't check with inspect because it's inside a print preview window. I'm just experimenting with a few things so no rush.  I will post an answer if I figure it out.

JS - called from onclick();

```<code>function print1() {
    window.print();
}
</code>```

CSS

```<code>    @media print{
    body *:not(#OFP_here){
        visibility: hidden;
        height:0px;
        margin: 0px;
        padding: 0px;
    }
</code>```

Update: 3 lines are due to a table that gets built by JS, even though I have accounted for the table in @media.

答:
You need to target the @page which will be what modifies the global page settings.  You can read more about it here at MDN

@page

The @page CSS at-rule is used to modify some CSS properties when printing a document.

Syntax

```<code>@page {
  margin: 1cm;
}
</code>```

Body:
My content in the print preview window is displaying down about 5 or 6 lines.

Since I've already dealt with height, margin & padding, I'm unsure what's keeping it down.  I can't check with inspect because it's inside a print preview window. I'm just experimenting with a few things so no rush.  I will post an answer if I figure it out.

JS - called from onclick();

function print1() {
    window.print();
}

CSS

    @media print{
    body *:not(#OFP_here){
        visibility: hidden;
        height:0px;
        margin: 0px;
        padding: 0px;
    }

Update: 3 lines are due to a table that gets built by JS, even though I have accounted for the table in @media.

Body:
You need to target the @page which will be what modifies the global page settings.  You can read more about it here at MDN

@page

The @page CSS at-rule is used to modify some CSS properties when printing a document.

Syntax

@page {
  margin: 1cm;
}


问:
How do I get the latest timestamp inserted in the dynamodb table?
I want to get the recent record added to the table from above (partition key = variable_key)

I did research and found out you can do this with
Query(hash_key=..., ScanIndexForward=True, limit=1)
But I m not getting the result can someone please explain me how should I do it?

答:
for those who are looking for answer, I solved this issue by storing timestamp of my last entry and then using scan and "LastEvaluatedKey".

Check the below code:
I stored my last entry with the timestamp, used scan and last evaluatedkey and then pandas df to sort out values.

```<code>response_variable=midstore.scan()
items_variable = r_variable['Items']
while 'LastEvaluatedKey' in r_variable:
    r_variable = midstore.scan(ExclusiveStartKey=r_variable['LastEvaluatedKey'])
    items_variable.extend(r_variable['Items'])
#print(r_variable)
last_df = pd.DataFrame(items_variable)
last_df["storage_key"]=pd.to_datetime(last_df["storage_key"]) ##Storage_key is the partition key from dynamodb table.

last_df=last_df.sort_values("storage_key")
last_element=last_df.iloc[-1]
#print(last_element["storage_key"])
LatestEntry = str(last_element['storage_key'])
#print(LatestEntry )
</code>```

Body:
for those who are looking for answer, I solved this issue by storing timestamp of my last entry and then using scan and "LastEvaluatedKey".

Check the below code:
I stored my last entry with the timestamp, used scan and last evaluatedkey and then pandas df to sort out values.

response_variable=midstore.scan()
items_variable = r_variable['Items']
while 'LastEvaluatedKey' in r_variable:
    r_variable = midstore.scan(ExclusiveStartKey=r_variable['LastEvaluatedKey'])
    items_variable.extend(r_variable['Items'])
#print(r_variable)
last_df = pd.DataFrame(items_variable)
last_df["storage_key"]=pd.to_datetime(last_df["storage_key"]) ##Storage_key is the partition key from dynamodb table.

last_df=last_df.sort_values("storage_key")
last_element=last_df.iloc[-1]
#print(last_element["storage_key"])
LatestEntry = str(last_element['storage_key'])
#print(LatestEntry )


问:
401 error message by retrieving author information from Scopus API
I am trying to use your Scopus API to retrieve the publications that a certain author has, but I am facing a 401 error message in the browser console:

```<code>GET https://api.elsevier.com/content/author/author_id/57196038163?apiKey=7f59af901d2d86f78a1fd60c1bf9426a&httpAccept=application/json 401
statusCode: "AUTHORIZATION_ERROR"
statusText: "The requestor is not authorized to access the requested view or fields of the resource"
</code>```

The API key is attached with my website URL

Please check the following page which generates the error:
https://evo-ml.com/raneem/scopus2.html

Code:

```<code><script>
fetch('https://api.elsevier.com/content/author/author_id/57196038163?apiKey=7f59af901d2d86f78a1fd60c1bf9426a&httpAccept=application/json')
.then(response => response.json())
.then(data => console.log(data))
.catch((error) => {console.error('Error:', error);});
</script>
</code>```

I also tried to test it through the URL: https://dev.elsevier.com/retrieval.html but it seems that there is a problem there too.

Note: I am testing it through the API key I got from the website (which I can't share here). the one I've provided is the testing API key from the website.

答:
The problem may be the network that you are using when sending the request. It should be the institution network, the same where the domain provided with the api key is registered.

Here is what you can read from the FAQ:

So if you are working from home the best way is to use VPN and/or remote desktop to send the request directly from the computer that is connected to the instutional network.

Body:
I am trying to use your Scopus API to retrieve the publications that a certain author has, but I am facing a 401 error message in the browser console:

GET https://api.elsevier.com/content/author/author_id/57196038163?apiKey=7f59af901d2d86f78a1fd60c1bf9426a&httpAccept=application/json 401
statusCode: "AUTHORIZATION_ERROR"
statusText: "The requestor is not authorized to access the requested view or fields of the resource"

The API key is attached with my website URL

Please check the following page which generates the error:
https://evo-ml.com/raneem/scopus2.html

Code:

I also tried to test it through the URL: https://dev.elsevier.com/retrieval.html but it seems that there is a problem there too.

Note: I am testing it through the API key I got from the website (which I can't share here). the one I've provided is the testing API key from the website.


问:
vue3 child component won't load with computed data as property
Here's the problem I'm having. I have a Leads page, that is my Leads.vue template. It loads my leads and then passes the leads data to other components via props.

The LeadSources component receives a computed method as it's property.
You can see that on the Leads.vue page, the LeadSources component calls the getSourceData() method for it's property data.

When I check the value of the props for LeadSources.vue in the setup() the value for chartData initially is an empty array. If the page hot-reloads then the LeadSources apexchart will populate with the :series data but otherwise I cannot get it to work.

Essentially it works like this.

Leads.vue passes getSourceData() to the LeadsSources.vue component which on the setup() sets it as the variable series and tries to load the apexchart with it.

It will not work if I refresh my page but if I save something in my IDE, the hot-reload will load the updated apexchart and the data appears. It seems like the prop values don't get set in the setup() function the first time around. How do I architecturally get around this? What's the proper way to set this up? I can't tell if the issue is on the leads.vue side of things or with the way that the LeadSources.vue component is being put together.

Any help would be appreciated, I've spent way too long trying to get this to work properly.

Leads.vue

```<code><template>
  <!--begin::Leads-->
  <div class="row gy-5 g-xl-8 mb-8">
    <div class="col-xxl-12">
      <LeadTracker
        :lead-data="leadData"
        :key="componentKey"
      />
    </div>
  </div>

  <div class="row gy-5 g-xl-8 mb-8">
    <div class="col-xxl-12">
      <LeadSources
        chart-color="primary"
        chart-height="500"
        :chart-data="getSourceData"
        :chart-threshold="sourceThreshold"
        widget-classes="lead-sources"
      ></LeadSources>
    </div>
  </div>
  <!--end::Leads-->
</template>

<script lang="ts">
import { defineComponent, defineAsyncComponent, onMounted } from "vue";
import { setCurrentPageTitle } from "@/core/helpers/breadcrumb";
import LeadSources from "@/components/leads/sources/LeadSources.vue";
import LeadTracker from "@/components/leads/tracker/LeadTracker.vue";
import LeadService from "@/core/services/LeadService";
import ApiService from "@/core/services/ApiService";
import {Lead} from "@/core/interfaces/lead";

export default defineComponent({
  name: "leads",
  components: {
    LeadTracker,
    LeadSources
  },
  data() {
    return {
      leadData: [] as Lead[],
    }
  },
  beforeCreate: async function() {
    this.leadData = await new LeadService().getLeads()
  },
  setup() {
    onMounted(() => {
      setCurrentPageTitle("Lead Activity");
    });

    const sourceThreshold = 5;

    return {
      sourceThreshold,
      componentKey: 0
    };
  },
  computed: {
    getSourceData() {
      interface SingleSource {
        source: string;
        value: number;
      }
      const sourceData: Array<SingleSource> = [];

      // Make array for source names
      const sourceTypes = [];
      this.leadData.filter(lead => {
        if (!sourceTypes.includes(lead.source)) sourceTypes.push(lead.source);
      });

      // Create objects for each form by name, push to leadSourceData
      sourceTypes.filter(type => {
        let totalSourceLeads = 1;
        this.leadData.filter(form => {
          if (form.source == type) totalSourceLeads++;
        });

        const leadSourceData = {
          source: type,
          value: totalSourceLeads
        };
        sourceData.push(leadSourceData);
      });

      // Sort by source popularity
      sourceData.sort(function(a, b) {
        return a.value - b.value;
      });

      return sourceData;
    }
  }
});
</script>
</code>```

LeadSources.vue

```<code><template>
  <!--begin::Lead Sources Widget-->
  <div :class="widgetClasses" class="card card-footprint">
    <!--begin::Body-->
    <div
      class="card-body p-0 d-flex justify-content-between flex-column overflow-hidden"
    >
      <div class="d-lg-flex flex-stack flex-grow-1 px-9 py-6">
        <!--begin::Text-->
        <div class="d-flex flex-column text-start col-lg-10">
          <span class="card-title">Lead Sources</span>
          <span class="card-description">Where your leads are coming from.</span>

          <!--begin::Chart-->
          <div class="d-flex flex-column">
            <apexchart
              class="mixed-widget-10-chart lead-sources-donut"
              :options="chartOptions"
              :series="series"
              type="donut"
              :height="chartHeight"
              :threshold="chartThreshold"
            ></apexchart>
          </div>
          <!--end::Chart-->
        </div>

        <!--begin::Unused Data-->
        <div class="d-flex flex-row flex-lg-column lg-col-2 justify-content-between unused-data">
          <div class="alt-sources flex-fill">
            <div><span class="alt-header">Other Sources:</span></div>
            <div v-for="item in otherSources" :key="item.source">
              <span>{{ item.source }}</span>
              <span>{{ item.value }}%</span>
            </div>
          </div>
          <div class="alt-sources flex-fill">
            <div><span class="alt-header">Sources Not Utilized:</span></div>
            <div v-for="item in unusedSources" :key="item.source">
              <span>{{ item.source }}</span>
            </div>
          </div>
        </div>
        <!--end::Unused Data-->
      </div>
    </div>
  </div>
  <!--end::Lead Sources Widget-->
</template>

<script lang="ts">
import { defineComponent, ref } from "vue";

export default defineComponent({
  name: "LeadSource",
  props: {
    widgetClasses: String,
    chartColor: String,
    chartHeight: String,
    chartLabels: Array,
    chartData: Array,
    chartThreshold: Number
  },
  setup(props) {
    const sum = (data) => {
      let total = 0;
      data?.map(function(v) {
        total += v;
      });
      return total;
    }

    const chartData = ref(props.chartData).value;

    const threshold = ref(props.chartThreshold).value;

    const usedSourcesLabel: string[] = [];
    const usedSourcesData: number[] = [];
    const otherSources: any = [];
    const unusedSources: any = [];

    const splitData = (data, max) => {
      // set used, other sources < 5%, unused sources
      data.filter((item) => {
        if (item.value > max) {
          usedSourcesLabel.push(item.source);
          usedSourcesData.push(item.value);
        } else if (item.value < max && item.value != 0 && item.value !== null) {
          otherSources.push(item);
        } else if (item.value == 0 || item.value === null) {
          unusedSources.push(item);
        }
      });
    };

    splitData(chartData, threshold);

    const chartOptions = {
      chart: {
        width: 380,
        type: "donut"
      },
      colors: [
        "#1C6767",
        "#CD2E3B",
        "#154D5D",
        "#F1D67E",
        "#4F9E82",
        "#EF8669",
        "#393939",
        "#30AEB4"
      ],
      plotOptions: {
        pie: {
          startAngle: -90,
          endAngle: 270
        }
      },
      dataLabels: {
        enabled: false
      },
      fill: {
        type: "gradient",
        gradient: {
          type: "horizontal",
          shadeIntensity: 0.5,
          opacityFrom: 1,
          opacityTo: 1,
          stops: [0, 100],
        }
      },
      legend: {
        show: true,
        position: "left",
        fontSize: "16px",
        height: 220,
        onItemClick: {
          toggleDataSeries: false
        },
        onItemHover: {
          highlightDataSeries: false
        },
        formatter: function (val, opts) {
          return val + " - " + opts.w.globals.series[opts.seriesIndex];
        }
      },
      title: {
        text: undefined
      },
      tooltip: {
        style: {
          fontSize: "14px"
        },
        marker: {
          show: false
        },
        y: {
          formatter: function(val) {
            return val + "%";
          },
          title: {
            formatter: (seriesName) => seriesName,
          },
        }
      },
      labels: usedSourcesLabel,
      annotations: {
        position: "front",
        yaxis: [{
          label: {
            text: "text annotation"
          }
        }],
        xaxis: [{
          label: {
            text: "text xaxis annotation"
          }
        }],
      },
      responsive: [{
        breakpoint: 480,
        options: {
          legend: {
            position: "bottom",
            horizontalAlign: "left"
          }
        }
      }]
    };
    const series = usedSourcesData;
    return {
      chartOptions,
      series,
      otherSources,
      unusedSources
    };
  }
});
</script>
</code>```

Edited

I will attach the LeadService.ts class as well as the ApiService.ts class so you can see where the data is coming from

LeadService.ts

```<code>import ApiService from "@/core/services/ApiService";
import {Lead} from "@/core/interfaces/lead";

export default class LeadService {

  getLeads() {

    const accountInfo = JSON.parse(localStorage.getItem('accountInfo') || '{}');

    ApiService.setHeader();

    return ApiService.query("/leads", {params: {client_id : accountInfo.client_id}})
      .then(({ data }) => {
        let leadData: Lead[] = data['Items'];
        return leadData;
      })
      .catch(({ response }) => {
        return response;
      });

  }
}
</code>```

ApiService.ts

```<code>import { App } from "vue";
import axios from "axios";
import VueAxios from "vue-axios";
import JwtService from "@/core/services/JwtService";
import { AxiosResponse, AxiosRequestConfig } from "axios";
import auth from "@/core/helpers/auth";

/**
 * @description service to call HTTP request via Axios
 */
class ApiService {
  /**
   * @description property to share vue instance
   */
  public static vueInstance: App;

  /**
   * @description initialize vue axios
   */
  public static init(app: App<Element>) {
    ApiService.vueInstance = app;
    ApiService.vueInstance.use(VueAxios, axios);
    ApiService.vueInstance.axios.defaults.baseURL = "https://api.domain.com/";
  }

  /**
   * @description set the default HTTP request headers
   */
  public static setHeader(): void {
    ApiService.vueInstance.axios.defaults.headers.common[
      "Authorization"
    ] = `Bearer ${auth.getSignInUserSession().getIdToken().jwtToken}`;
    ApiService.vueInstance.axios.defaults.headers.common[
      "Content-Type"
    ] = "application/json application/vnd.api+json";
  }

  /**
   * @description send the GET HTTP request
   * @param resource: string
   * @param params: AxiosRequestConfig
   * @returns Promise<AxiosResponse>
   */
  public static query(
    resource: string,
    params: AxiosRequestConfig
  ): Promise<AxiosResponse> {
    return ApiService.vueInstance.axios.get(resource, params).catch(error => {
      // @TODO log out and send home if response is 401 bad auth
      throw new Error(`[KT] ApiService ${error}`);
    });
  }
}

export default ApiService;
</code>```

答:
I think the issue is caused when you're calling the data from the api.
This code:

```<code>beforeCreate: async function() {
    this.leadData = await new LeadService().getLeads()
},
</code>```

I'd refactor to

```<code>async created () {
    const service = new LeadService()
    const value = await service.getLeads()
}
</code>```

Also it would be nice to be able to see how you're fetching your data.
Sometimes this code: const value = await axios.get('/api/getStuff').data can be problematic because of paratheses issues. Which causes the same issue you described of, hot reloading working, but fresh not. I suspect the same sort of issue relies of the code executing like => (await new LeadService()).getLeads() Where you're probably awaiting the class, rather than the actual async code.

Body:
Here's the problem I'm having. I have a Leads page, that is my Leads.vue template. It loads my leads and then passes the leads data to other components via props.

The LeadSources component receives a computed method as it's property.
You can see that on the Leads.vue page, the LeadSources component calls the getSourceData() method for it's property data.

When I check the value of the props for LeadSources.vue in the setup() the value for chartData initially is an empty array. If the page hot-reloads then the LeadSources apexchart will populate with the :series data but otherwise I cannot get it to work.

Essentially it works like this.

Leads.vue passes getSourceData() to the LeadsSources.vue component which on the setup() sets it as the variable series and tries to load the apexchart with it.

It will not work if I refresh my page but if I save something in my IDE, the hot-reload will load the updated apexchart and the data appears. It seems like the prop values don't get set in the setup() function the first time around. How do I architecturally get around this? What's the proper way to set this up? I can't tell if the issue is on the leads.vue side of things or with the way that the LeadSources.vue component is being put together.

Any help would be appreciated, I've spent way too long trying to get this to work properly.

Leads.vue

<template>

      <LeadTracker
        :lead-data="leadData"
        :key="componentKey"
      />

      <LeadSources
        chart-color="primary"
        chart-height="500"
        :chart-data="getSourceData"
        :chart-threshold="sourceThreshold"
        widget-classes="lead-sources"
      ></LeadSources>

</template>

LeadSources.vue

<template>

          Lead Sources
          Where your leads are coming from.

            <apexchart
              class="mixed-widget-10-chart lead-sources-donut"
              :options="chartOptions"
              :series="series"
              type="donut"
              :height="chartHeight"
              :threshold="chartThreshold"
            ></apexchart>

Other Sources:

              {{ item.source }}
              {{ item.value }}%

Sources Not Utilized:

              {{ item.source }}

</template>

Edited

I will attach the LeadService.ts class as well as the ApiService.ts class so you can see where the data is coming from

LeadService.ts

import ApiService from "@/core/services/ApiService";
import {Lead} from "@/core/interfaces/lead";

export default class LeadService {

  getLeads() {

    const accountInfo = JSON.parse(localStorage.getItem('accountInfo') || '{}');

    ApiService.setHeader();

    return ApiService.query("/leads", {params: {client_id : accountInfo.client_id}})
      .then(({ data }) => {
        let leadData: Lead[] = data['Items'];
        return leadData;
      })
      .catch(({ response }) => {
        return response;
      });

  }
}

ApiService.ts

import { App } from "vue";
import axios from "axios";
import VueAxios from "vue-axios";
import JwtService from "@/core/services/JwtService";
import { AxiosResponse, AxiosRequestConfig } from "axios";
import auth from "@/core/helpers/auth";

/**
 * @description service to call HTTP request via Axios
 */
class ApiService {
  /**
   * @description property to share vue instance
   */
  public static vueInstance: App;

  /**
   * @description initialize vue axios
   */
  public static init(app: App<Element>) {
    ApiService.vueInstance = app;
    ApiService.vueInstance.use(VueAxios, axios);
    ApiService.vueInstance.axios.defaults.baseURL = "https://api.domain.com/";
  }

  /**
   * @description set the default HTTP request headers
   */
  public static setHeader(): void {
    ApiService.vueInstance.axios.defaults.headers.common[
      "Authorization"
    ] = `Bearer ${auth.getSignInUserSession().getIdToken().jwtToken}`;
    ApiService.vueInstance.axios.defaults.headers.common[
      "Content-Type"
    ] = "application/json application/vnd.api+json";
  }

  /**
   * @description send the GET HTTP request
   * @param resource: string
   * @param params: AxiosRequestConfig
   * @returns Promise<AxiosResponse>
   */
  public static query(
    resource: string,
    params: AxiosRequestConfig
  ): Promise<AxiosResponse> {
    return ApiService.vueInstance.axios.get(resource, params).catch(error => {
      // @TODO log out and send home if response is 401 bad auth
      throw new Error(`[KT] ApiService ${error}`);
    });
  }
}

export default ApiService;

Body:
I think the issue is caused when you're calling the data from the api.
This code:

beforeCreate: async function() {
    this.leadData = await new LeadService().getLeads()
},

I'd refactor to

async created () {
    const service = new LeadService()
    const value = await service.getLeads()
}

Also it would be nice to be able to see how you're fetching your data.
Sometimes this code: const value = await axios.get('/api/getStuff').data can be problematic because of paratheses issues. Which causes the same issue you described of, hot reloading working, but fresh not. I suspect the same sort of issue relies of the code executing like => (await new LeadService()).getLeads() Where you're probably awaiting the class, rather than the actual async code.


问:
print/modify the Redux store using Chrome Dev Tools's console
I find it useful to be able to print/modify the Redux store via Chrome Dev Tools's console, however to do this I have to copy the store in the window component as follows:

```<code>window.store = store;

render(
    <Provider store={store}>
        <App />
    </Provider>,
    document.getElementById("root")
);
</code>```

this way I can later use the console to print for instance the content of the store with window.store.getState():

How can I access the store inside the provider directly via the console?

答:
I want to suggest an alternative: use the Redux Devtools. They are available as a Chrome or Firefox extension, allow you to see current and all past states and all dispatched actions.

If you follow the official recommendations and use Redux Toolkit for your Redux code (modern Redux does not use hand-written switch..case reducers for years any more even though outdated tutorials unfortunately show that; if you need an up-to-date tutorial use the official Redux tutorial), using configureStore will even set up the devtools up for you correctly.

Body:
I find it useful to be able to print/modify the Redux store via Chrome Dev Tools's console, however to do this I have to copy the store in the window component as follows:

window.store = store;

render(
    <Provider store={store}>
        <App />
    </Provider>,
    document.getElementById("root")
);

this way I can later use the console to print for instance the content of the store with window.store.getState():

How can I access the store inside the provider directly via the console?


问:
HTML. Make Website Fit Other Devices And Screens?
I recently got "done" with a website (http://calcultr.comxa.com/). It looks fine on my screen, but on my friends' screen it does not fit the screen. The same with my other devices. I have added this to the Head tag:

```<code><meta name="apple-mobile-web-app-capable" content="yes">
<meta content="text/html; charset=utf-8" http-equiv="content-type">
<meta name="viewport" content="width=device-width, intial-scale=1">
</code>```

I have heard many people saying "that will fix the problem", but it didn't. I don't even know what it means. Were they lying?
How would I make my website fit any device and screens?

答:
You can do it with bootstrap</p>
```<code><html>enter code here
<head>
<title>FORM PAGE</title>
    <link href="css/bootstrap.min.css" rel="stylesheet">
</head>
<body style="background: #eee">
    <div class="container p-2 mt-5" style="background: #fff">
       <div class="row mt-5 text-center">
        <div class="col-md-10 col-12">
           <form>
              <label>enter your name</label>
               <input type="text" placeholder="enter your name" id="name"><br><br>

               <label>enter your age</label>
               <input type="text" placeholder="enter your age" id="age"><br><br>

               <label>enter your phone number</label>
               <input type="text" placeholder="enter your phone" id="phone"><br><br>

               <button id="add" type="button" class="btn btn-primary">insert</button>

            </form>
           </div>
        </div>
    </div>
</body>

</html>
</code>```

Body:
I recently got "done" with a website (http://calcultr.comxa.com/). It looks fine on my screen, but on my friends' screen it does not fit the screen. The same with my other devices. I have added this to the Head tag:

<meta name="apple-mobile-web-app-capable" content="yes">
<meta content="text/html; charset=utf-8" http-equiv="content-type">
<meta name="viewport" content="width=device-width, intial-scale=1">

I have heard many people saying "that will fix the problem", but it didn't. I don't even know what it means. Were they lying?
How would I make my website fit any device and screens?

Body:
You can do it with bootstrap

<html>enter code here
<head>
<title>FORM PAGE</title>
    <link href="css/bootstrap.min.css" rel="stylesheet">
</head>
<body style="background: #eee">
    <div class="container p-2 mt-5" style="background: #fff">
       <div class="row mt-5 text-center">
        <div class="col-md-10 col-12">
           <form>
              <label>enter your name</label>
               <input type="text" placeholder="enter your name" id="name"><br><br>

               <label>enter your age</label>
               <input type="text" placeholder="enter your age" id="age"><br><br>

               <label>enter your phone number</label>
               <input type="text" placeholder="enter your phone" id="phone"><br><br>

               <button id="add" type="button" class="btn btn-primary">insert</button>

            </form>
           </div>
        </div>
    </div>
</body>

</html>


问:
Oauth cookie authentication with cross domain in ASP.NET Core API
I have used OAuth cookie authentication in the ASP.NET Core API project. All the APIs are authorized in this project. After successful login, all APIs can be accessible from a browser URL bar. When I try to access APIs in AJAX request from other domains always this will return Unauthorized.

Here how to identify the user is authenticated or not from AJAX request?

```<code>API domain = ".apidomain.com"
Client domain = ".clientdomain.com"
</code>```

API configuration:

```<code>services.AddAuthentication("oAuthSecurityScheme")
                .AddOAuth("login.microsoftonline.com",
                options =>
                {
                   ....
                   ....
                }).AddCookie(
                "oAuthSecurityScheme",
                options =>
                {
                options.LogoutPath = new PathString("/logout");
                options.LoginPath = new PathString("/api/v1/account/authorize");
                options.ExpireTimeSpan = new TimeSpan(7, 0, 0, 0);
                options.SlidingExpiration = true;
                options.Cookie.Name = "CustomerOAuthCookie";
                options.Events.OnRedirectToLogin = UnAuthorizedResponseAsync;
                options.Cookie.SameSite = SameSiteMode.None;
                options.Cookie.HttpOnly = false;
            });
</code>```

Client Application:

```<code>$.ajax({
       url: "https://localhost:44332/api/gettickets/1",
       type: 'GET',
       success: function (result)
       {
          alert(result);
          console.log(result);
       }
});
</code>```

Note: When I access the below API in the browser directly it will return the proper response
       https://localhost:44332/api/gettickets/1

答:
I usually prefer using tokens in order to send and save authorization data and suggest to you that.
but if you still want to use cookie follow the below link way:

jquery ajax call not sending cookie

Body:
I have used OAuth cookie authentication in the ASP.NET Core API project. All the APIs are authorized in this project. After successful login, all APIs can be accessible from a browser URL bar. When I try to access APIs in AJAX request from other domains always this will return Unauthorized.

Here how to identify the user is authenticated or not from AJAX request?

API domain = ".apidomain.com"
Client domain = ".clientdomain.com"

API configuration:

services.AddAuthentication("oAuthSecurityScheme")
                .AddOAuth("login.microsoftonline.com",
                options =>
                {
                   ....
                   ....
                }).AddCookie(
                "oAuthSecurityScheme",
                options =>
                {
                options.LogoutPath = new PathString("/logout");
                options.LoginPath = new PathString("/api/v1/account/authorize");
                options.ExpireTimeSpan = new TimeSpan(7, 0, 0, 0);
                options.SlidingExpiration = true;
                options.Cookie.Name = "CustomerOAuthCookie";
                options.Events.OnRedirectToLogin = UnAuthorizedResponseAsync;
                options.Cookie.SameSite = SameSiteMode.None;
                options.Cookie.HttpOnly = false;
            });

Client Application:

$.ajax({
       url: "https://localhost:44332/api/gettickets/1",
       type: 'GET',
       success: function (result)
       {
          alert(result);
          console.log(result);
       }
});

Note: When I access the below API in the browser directly it will return the proper response
       https://localhost:44332/api/gettickets/1


问:
Why does my autoplay not consistently work on mobile devices?
I have a website with a video that is supposed to autoplay. Last week it was working on both the web browser and mobile devices, but now the video will not autoplay on my mobile device despite the code being the same, and I have to hit a play button for the video to start. The video still autoplays in the web browser. Does anyone know why this is? I have attached an image of my code below.

Code Image

答: If you are viewing it on Safari on IOS and the video does not have any sound it does not work. See the compatibility here.</p>


问:
elininate some lines from data set
I am rying to get some line out of my data set.

```<code>#!/usr/local/bin/perl
use Date::Calc qw(Add_Delta_Days);
my @just_ecps;
my @folder_dates;
my @ecp_dot_tee_array = `grep ISLAND ~/data/files/grit.t`;
foreach (@ecp_dot_tee_array){
      ($ecp, undef, undef, undef, undef, undef) = split (/\s+/, $_);
         push (@just_ecps, $ecp);
}
for ($h = 1; $h <= 5; $h++){

   my (undef, undef, undef, $day, $month, $year) = localtime();
   $year+=1900;
   $month+=1;
   ($year, $month, $day) = Add_Delta_Days($year, $month, $day, -$h );
   if ($month < 10 ){
      $month = "0$month";
   }
   if ($day < 10 ){
      $day = "0$day";
   }
push (@folder_dates, "$year$month$day");
}

for ( $j=0; $j <=$#just_ecps ; $j++){
   for ($x=0; $x<=$#folder_dates ; $x++){
      open FILEHANDLE , "zmore /data/ibprod/archive/$folder_dates[$x]/$just_ecps[$j]  /ghistogram.gz | ";
      @archive_average = (<FILEHANDLE>);
      foreach $line(@archive_average){
         if ($line =~ /ave:\s+(\d+\.\d+)\s/){
            print $1;
            sleep 1;
            print "\n";
         }
      }
   }
}
</code>```

This is what i get when i run the program - i am trying to get the 'cannot read the > files out of the data set

```<code>% ./read_in_ghistogram2
0.00414601
0.0044511
0.00387373
/usr/bin/zmore: line 52: /home/data/archive/20110814/islnd1/ghistogram.gz: No such  file or directory
/usr/bin/zmore: line 52: /home/data/archive/20110813/islnd1/ghistogram.gz: No such file or directory
0.00309721
0.00302753
0.00307702
/usr/bin/zmore: line 52: /home/data/archive/20110814/islnd2/ghistogram.gz: No such file or directory
/usr/bin/zmore: line 52: /home/data/archive/20110813/islnd2/ghistogram.gz: No such file or directory
0.00324729
0.00295381
0.00301736
/usr/bin/zmore: line 52: /home/data/archive/20110814/islnd3/ghistogram.gz: No such file or directory
/usr/bin/zmore: line 52: /home/data/archive/20110813/islnd3/ghistogram.gz: No such file or directory
</code>```

I tried filtering them out of the while loop, but it does not work, and ther is not line 52 in the program, it only goes to 42

```<code>for ( $j=0; $j <=$#just_ecps ; $j++){
   for ($x=0; $x<=$#folder_dates ; $x++){
      #print "/home/ibprod_archive/$folder_dates[$x]/$just_ecps[$j]/ghistogram.gz";
      open FILEHANDLE , "zmore /data/archive/$folder_dates[$x]/$just_ecps[$j]/ghistogram.gz | ";
      while (<FILEHANDLE>) {
          next if ($_ =~ '/No such file or directory/');
          push (@archive_average,$_);
          foreach $line(@archive_average){
             if ($line =~ /\save:\s+(\d+\.\d+)\s/){
               print $line;
               sleep 1;
             }
         }
      }
   }
</code>```

答:
Line 52 refers to the line in the zmore script, not in your perl script.

To fix your issue, test if the file exists in your perl script before handing it over to something else.

```<code>my $archive = "/data/archive/$folder_dates[$x]/$just_ecps[$j]/ghistogram.gz";
next unless (-r $archive);
</code>```

-r checks both that the file exists and is readable by the current user. So next unless (-r $file) will go to the next iteration of the loop unless the file exists and is readable.

(This is racy - if something is removing (or changing ownership of) those files while you are trying to read them, open can still fail. If this is not security sensitive, then that's not too much of a worry, but keep that in mind.)

Two tips:

zmore is meant to be used by humans, not scripts. You script does not care one bit if the output is paginated. So you should be using gunzip -c $file (or maybe gzip -cd if you don't have gunzip, not sure about that one).

Always check that open succeeded, otherwise you'll be trying to manipulate invalid filehandles at some point, which will get you more errors. And always close what you opened.

So I'd change your script to:

```<code>my $archive = "/data/archive/$folder_dates[$x]/$just_ecps[$j]/ghistogram.gz";
next unless (-r $archive);
if (!open(FILEHANDLE, "<", "gunzip -c $archive|")) {
  print STDERR "Error processing $archive: $!\n"; # optional
  next;
}
while (<FILEHANDLE>) {
  ...
}
close FILEHANDLE;
</code>```

Lastly, the zmore error message is being printed to STDERR. If all you want to do is hide those messages (rather than fixing them), simply redirect that to a log file (or /dev/null):

```<code>% ./read_in_ghistogram2 2> errors.log
</code>```

Title: elininate some lines from data set

Body:
I am rying to get some line out of my data set.

#!/usr/local/bin/perl
use Date::Calc qw(Add_Delta_Days);
my @just_ecps;
my @folder_dates;
my @ecp_dot_tee_array = `grep ISLAND ~/data/files/grit.t`;
foreach (@ecp_dot_tee_array){
      ($ecp, undef, undef, undef, undef, undef) = split (/\s+/, $_);
         push (@just_ecps, $ecp);
}
for ($h = 1; $h <= 5; $h++){

   my (undef, undef, undef, $day, $month, $year) = localtime();
   $year+=1900;
   $month+=1;
   ($year, $month, $day) = Add_Delta_Days($year, $month, $day, -$h );
   if ($month < 10 ){
      $month = "0$month";
   }
   if ($day < 10 ){
      $day = "0$day";
   }
push (@folder_dates, "$year$month$day");
}

for ( $j=0; $j <=$#just_ecps ; $j++){
   for ($x=0; $x<=$#folder_dates ; $x++){
      open FILEHANDLE , "zmore /data/ibprod/archive/$folder_dates[$x]/$just_ecps[$j]  /ghistogram.gz | ";
      @archive_average = (<FILEHANDLE>);
      foreach $line(@archive_average){
         if ($line =~ /ave:\s+(\d+\.\d+)\s/){
            print $1;
            sleep 1;
            print "\n";
         }
      }
   }
}

This is what i get when i run the program - i am trying to get the 'cannot read the > files out of the data set

% ./read_in_ghistogram2
0.00414601
0.0044511
0.00387373
/usr/bin/zmore: line 52: /home/data/archive/20110814/islnd1/ghistogram.gz: No such  file or directory
/usr/bin/zmore: line 52: /home/data/archive/20110813/islnd1/ghistogram.gz: No such file or directory
0.00309721
0.00302753
0.00307702
/usr/bin/zmore: line 52: /home/data/archive/20110814/islnd2/ghistogram.gz: No such file or directory
/usr/bin/zmore: line 52: /home/data/archive/20110813/islnd2/ghistogram.gz: No such file or directory
0.00324729
0.00295381
0.00301736
/usr/bin/zmore: line 52: /home/data/archive/20110814/islnd3/ghistogram.gz: No such file or directory
/usr/bin/zmore: line 52: /home/data/archive/20110813/islnd3/ghistogram.gz: No such file or directory

I tried filtering them out of the while loop, but it does not work, and ther is not line 52 in the program, it only goes to 42

for ( $j=0; $j <=$#just_ecps ; $j++){
   for ($x=0; $x<=$#folder_dates ; $x++){
      #print "/home/ibprod_archive/$folder_dates[$x]/$just_ecps[$j]/ghistogram.gz";
      open FILEHANDLE , "zmore /data/archive/$folder_dates[$x]/$just_ecps[$j]/ghistogram.gz | ";
      while (<FILEHANDLE>) {
          next if ($_ =~ '/No such file or directory/');
          push (@archive_average,$_);
          foreach $line(@archive_average){
             if ($line =~ /\save:\s+(\d+\.\d+)\s/){
               print $line;
               sleep 1;
             }
         }
      }
   }

Body:
Line 52 refers to the line in the zmore script, not in your perl script.

To fix your issue, test if the file exists in your perl script before handing it over to something else.

my $archive = "/data/archive/$folder_dates[$x]/$just_ecps[$j]/ghistogram.gz";
next unless (-r $archive);

-r checks both that the file exists and is readable by the current user. So next unless (-r $file) will go to the next iteration of the loop unless the file exists and is readable.

(This is racy - if something is removing (or changing ownership of) those files while you are trying to read them, open can still fail. If this is not security sensitive, then that's not too much of a worry, but keep that in mind.)

Two tips:

zmore is meant to be used by humans, not scripts. You script does not care one bit if the output is paginated. So you should be using gunzip -c $file (or maybe gzip -cd if you don't have gunzip, not sure about that one).

Always check that open succeeded, otherwise you'll be trying to manipulate invalid filehandles at some point, which will get you more errors. And always close what you opened.

So I'd change your script to:

my $archive = "/data/archive/$folder_dates[$x]/$just_ecps[$j]/ghistogram.gz";
next unless (-r $archive);
if (!open(FILEHANDLE, "<", "gunzip -c $archive|")) {
  print STDERR "Error processing $archive: $!\n"; # optional
  next;
}
while (<FILEHANDLE>) {
  ...
}
close FILEHANDLE;

Lastly, the zmore error message is being printed to STDERR. If all you want to do is hide those messages (rather than fixing them), simply redirect that to a log file (or /dev/null):

% ./read_in_ghistogram2 2> errors.log