Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/google-sheets/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Google apps script 访问正确的范围时;论编辑;触发函数修改Google工作表';s结构_Google Apps Script_Google Sheets_Triggers_Eventtrigger - Fatal编程技术网

Google apps script 访问正确的范围时;论编辑;触发函数修改Google工作表';s结构

Google apps script 访问正确的范围时;论编辑;触发函数修改Google工作表';s结构,google-apps-script,google-sheets,triggers,eventtrigger,Google Apps Script,Google Sheets,Triggers,Eventtrigger,如果输入了特定值,我需要将一行移动到另一个工作表,例如存档数据 我已经编写了下面的代码,只要用户在第一次触发完成之前没有再次触发它,它就可以完美地工作。第一个事件将移动相应的行,但第二个“编辑”事件将移动不同的行,因为行数已被上一个onEdit()调用更改。例如: 客户编辑第[1]行和第[3]行,并将其标记为存档 第一个onEdit将删除行[1],因此行[3]将成为行[2],但在第二个onEdit调用中,范围。getRow()仍返回3,因此行[3]将被删除,而不是行[2] function on

如果输入了特定值,我需要将一行移动到另一个工作表,例如存档数据

我已经编写了下面的代码,只要用户在第一次触发完成之前没有再次触发它,它就可以完美地工作。第一个事件将移动相应的行,但第二个“编辑”事件将移动不同的行,因为行数已被上一个
onEdit()
调用更改。例如:

客户编辑第[1]行和第[3]行,并将其标记为存档

第一个
onEdit
将删除
行[1]
,因此
行[3]
将成为
行[2]
,但在第二个
onEdit
调用中,
范围。getRow()
仍返回3,因此
行[3]
将被删除,而不是
行[2]

function onEdit(event)
{
  moveArchived(event);
}

function moveArchived(event)
{
  var sheetNameToWatch = "Queue";
  var columnNumberToWatch = 15; // column A = 1, B = 2, O = 15, etc.
  var valueToWatch = "ARCHIVE";
  var sheetNameToMoveTheRowTo = "Archive";

  var ss = SpreadsheetApp.getActiveSpreadsheet();
  var sheet = event.source.getActiveSheet();
  var range = event.source.getActiveCell();

  if (sheet.getName() == sheetNameToWatch && range.getColumn() == columnNumberToWatch && range.getValue() == valueToWatch)
  {
    var ui = SpreadsheetApp.getUi();
    var response = ui.alert('Do you want to move this row to Archive sheet?', ui.ButtonSet.YES_NO);
    if (response == ui.Button.NO)
      return;

    var targetSheet = ss.getSheetByName(sheetNameToMoveTheRowTo);
    var targetRange = targetSheet.getRange(targetSheet.getLastRow() + 1, 1);
    sheet.getRange(range.getRow(), 1, 1, sheet.getLastColumn()).moveTo(targetRange);
    sheet.deleteRow(range.getRow());
  }  
}
如何修改代码来防止这种情况,即确保移动实际范围?

我认为使用将是此用例的理想解决方案,因为它的目的是防止两个或多个函数执行之间的并发,但我对得到的结果有点失望

也许有人会找到更好的方法来实现它,或者提出另一种解决方案;-)

同时,您可以尝试下面的代码。我做了一些更改,其中之一是能够同时处理多个单元格(如果用户粘贴了多个包含“存档”的单元格)

我还使用来自事件本身的范围更改了范围定义,最后,我使用了一个可安装的OneEdit,而不是简单的OneEdit,因为我觉得它工作起来更可靠(尽管没有客观原因……可能是我梦到的;-)) 并更改了onEdit函数名以避免双重触发

因此,您必须从脚本编辑器的Resources菜单添加一个新的OneEdit触发器

在所有这些警告之后,我唯一能说的是它是有效的。。。但并非总是如此!这是使用脚本时最烦人的情况。。。所以,正如我已经说过的,在买之前先试试,然后祈祷有人能很快改进

代码如下:

function moveArchived(event){
  var lock = LockService.getPublicLock();
  // Wait for up to 30 seconds for other processes to finish.
  lock.waitLock(30000);
  var sheetNameToWatch = "Queue";
  var columnNumberToWatch = 15; // column A = 1, B = 2, O = 15, etc.
  var valueToWatch = "ARCHIVE";
  var sheetNameToMoveTheRowTo = "Archive";

  var ss = SpreadsheetApp.getActiveSpreadsheet();
  var sheet = event.source.getActiveSheet();
  var range = event.range;

  if (sheet.getName() == sheetNameToWatch && range.getColumn() == columnNumberToWatch && range.getValue().indexOf(valueToWatch)>-1)
  {
    var ui = SpreadsheetApp.getUi();
    var response = ui.alert('Do you want to move this/these row(s) to Archive sheet?', ui.ButtonSet.YES_NO);
    if (response == ui.Button.NO)
    {
      lock.releaseLock();
      return
    }
    var targetSheet = ss.getSheetByName(sheetNameToMoveTheRowTo);
    var targetRange = targetSheet.getRange(targetSheet.getLastRow() + 1, 1);
    range.moveTo(targetRange);
    for(var n = event.range.rowStart ; n < event.range.rowEnd ; n++){
      sheet.deleteRow(n);
    }
  }  
  lock.releaseLock();
}

function installOnEdit(event){
  Logger.log(JSON.stringify(event));
  moveArchived(event);
}
函数(事件){
var lock=LockService.getPublicLock();
//等待30秒,等待其他进程完成。
lock.waitLock(30000);
var sheetnametwatch=“队列”;
var columnNumberToWatch=15;//列A=1、B=2、O=15等。
var valueToWatch=“存档”;
var sheetnametomovetherowt=“存档”;
var ss=SpreadsheetApp.getActiveSpreadsheet();
var sheet=event.source.getActiveSheet();
var范围=事件范围;
如果(sheet.getName()==sheetNameToWatch&&range.getColumn()==columnNumberToWatch&&range.getValue().indexOf(valueToWatch)>-1)
{
var ui=SpreadsheetApp.getUi();
var response=ui.alert('是否要将此/这些行移动到存档工作表?',ui.ButtonSet.YES\u NO);
如果(响应==ui.Button.NO)
{
锁。释放锁();
返回
}
var targetSheet=ss.getSheetByName(sheetnametomovetherowt);
var targetRange=targetSheet.getRange(targetSheet.getLastRow()+1,1);
范围。移动到(目标范围);
对于(var n=event.range.rowStart;n