Posts mit dem Label HRESULT werden angezeigt. Alle Posts anzeigen
Posts mit dem Label HRESULT werden angezeigt. Alle Posts anzeigen

Freitag, 12. Dezember 2008

Fehler beim Anlegen eines Folders in einer Dokumentenbibliothek

Einen sehr merkwürdigen Fehler habe ich bei unserem aktuellen Projekt - einer Migration von Livelink nach SharePoint - entdeckt und gelöst.

Hier werden u.a. programmatisch Folder und Dokumente in einer Dokumentenbibliothek angelegt aber ab und zu taucht diese Fehlermeldung auf:

The filename, directory name, or volume label syntax is incorrect. (Exception from HRESULT: 0x8007007B)

Der Name des anzulegenden Folders war "1_ERF ", beinhaltete also keine Zeichen, die SharePoint kategorisch ablehnt (wie z.B. & # % * usw.). Über die Oberfläche war der Folder ebenfalls problemlos anlegbar.
Daraufhin versuchte ich noch einmal den Folder programmatisch anzulegen. Diesmal ohne das Leerzeichen am Ende und siehe da, plötzlich funktionierte es problemlos.

Fazit: Beim programmatischen Anlegen von Foldern in einer Dokumentenbibliothek am besten immer ein .TrimEnd() oder .Trim() an den Folder-Namen hängen.

Montag, 14. Juli 2008

Probleme beim Updaten von SPFieldLookup-Objekten

Ein Lookup-Feld programmatisch auf eine Liste verlinken ist ein Kinderspiel: einfach die Attribute LookupList mit der GUID der auswählbaren Liste und LookupWebId mit der jeweiligen WebID belegen. Fertig!...

Von wegen! Das ganze funktioniert nämlich nur, solange der aktuelle Benutzer Site Collection Administrator ist.

Wird das von einem User, der nicht Site Collection Administrator ist, angestoßen, kracht es und der Aufruf
spFieldLookup.LookupWebId = spRootWeb.ID;

wirft eine System.UnauthorizedAccessException: Access is denied, bzw. Exception from HRESULT: 0x80070005 (E_ACCESSDENIED)

Eine Lösung für das Problem bietet das SDK durch den Einsatz der Methode SPSecurity.RunWithElevatedPrivileges, der ein delegate übergeben werden kann in dem dann der jeweilige Code ausgeführt wird.

Laut SDK wird die spezifizierte Methode mit FULL CONTROL-Rechten ausgeführt, egal, ob der User diese Rechte besitzt oder nicht.

Ein Beispiel dafür findet sich in der MSDN: *click*

Bei uns sieht das dann in etwa so aus (ich habe ein paar Code-Zeilen der Übersichtlichkeit halber ausgelassen):

SPSecurity.RunWithElevatedPrivileges(delegate()
{
SPWeb site = (SPWeb)properties.Feature.Parent;
SPSite siteColl = site.Site;

// get current site
using (SPSite elevatedSiteColl = new SPSite(siteColl.ID))
{
// get current web
using (SPWeb spCurrentWeb = elevatedSiteColl.OpenWeb(site.ID))
{
// get rootweb from this web's parent site
using (SPWeb spRootWeb = (SPWeb)spCurrentWeb.Site.RootWeb)
{
...anderer code, der z.b. die liste, auf die das lookup-feld referenzieren soll, einlist...

SPFieldLookup spFieldLookup = (SPFieldLookup)spList.Fields.GetFieldByInternalName(lookupInfo.FieldInternalName);
spFieldLookup.LookupWebId = spRootWeb.ID;
spFieldLookup.LookupList = listGuid.ToString();
spFieldLookup.Update();
}
}
}
}
});

Ganz wichtig ist, dass die aktuelle SiteCollection, neu instanziiert wird. Ansonsten wird das SPSite-Objekt des aktuellen Users benutzt was ja ausserhalb des SPSecurity.RunWithElevatedPrivileges-Kontexted generiert wurde und daher keine Berechtigung hat, das Lookup-Feld zu verändern.

Meiner Meinung nach sollte diese Methode wirklich nur an Stellen benutzt werden, an denen es keine Alternative gibt, da sie das Sicherheitskonzept völlig aushebelt und dem Code, der vom aktuellen Benutzer ausgeführt wird, viele Rechte gewährt...

Mittwoch, 2. Juli 2008

BDC-Felder und die Fehlermeldung HRESULT 0x80040e14

Eine Anforderung in unserem aktuellen Projekt ist es, in einer von uns erstellten Benutzerdefinierten Liste (Custom List) Business Data Catalog-Felder (BDC-Felder) anzubieten. Um sie in unsere Solution zu integrieren, sind wir bisher so vorgegangen:

  1. BDC-Feld der Liste manuell hinzufügen
  2. Liste mit Hilfe des Solution Generators extrahieren
  3. Felddefinition aus der extrahierten schema.xml übernehmen und in unsere vorhandenen .xml-Files einbinden:
  • eine s2sfields.xml, die sämtliche unserer verwendeten Website-Columns beinhaltet
  • eine s2stypes.xml, die unsere verwendeten ContentTypes beinhaltet und
  • die schema.xml, die unser Listentemplate beschreibt
Nachdem wir die Solution dann installiert hatten und einen Eintrag in der Liste vornehmen wollten, kam, nachdem wir das Formular abschickten, diese Fehlermeldung:

HRESULT: 0x80040e14

Nach einiger Verzweiflung und rumgegoogle haben wir uns dann das SharePoint-Log noch einmal genauer angesehen und sind dann auf diese Fehlermeldung gestoßen, die uns tatsächlich einmal weiter geholfen hat:

Unexpected query execution failure, error code 8143. Additional error information from SQL Server is included below. "Der '@nvarchar3'-Parameter wurde mehrmals bereitgestellt." Query text (if available): "SET NOCOUNT ON; DECLARE @ItemId int,@@iRet int,@ExtraItemSize int,@DN nvarchar(256),@LN nvarchar(128),@@S uniqueidentifier,@@DocUIVersion int,@@Level tinyint;SET @@S='91713DD8-88FA-448A-8596-67313E781F4F';SET @@Level=1;SET @@DocUIVersion = 512;BEGIN TRAN;SET @ItemId=NULL;SET @DN=N'websites/speed2sales/as1/Lists/BasicList';SET @LN=NULL;SELECT @ExtraItemSize = 0 EXEC @@iRet = proc_AddListItem @SiteId = '91713DD8-88FA-448A-8596-67313E781F4F',@WebId='0770642C-837D-4897-AF07-1B28D3F0C212',@ListID = 'F9870FF9-DA52-40F3-A77A-80D98A7F461B',@RowOrdinal = 0,@ItemDocType = 0,@ItemId = @ItemId OUTPU...
Unexpected ...T,@ItemDirName=@DN OUTPUT,@ItemLeafName=@LN OUTPUT,@UserID = 1,@TimeNow = '20080702 13:40:20',@ServerTemplate = 100,@Basetype= 0,@Level= 1,@tp_GUID ='03863A1B-2194-41FC-911F-D85A480DC4B8',@AddNamespace=1,@CheckDiskQuota=1, @tp_ContentTypeId = ?, @nvarchar29 = ?, @nvarchar32 = ?, @nvarchar33 = ?, @nvarchar34 = ?, @int1 = ?, @nvarchar2 = ?, @nvarchar28 = ?, @nvarchar3 = ?, @nvarchar4 = ?, @nvarchar5 = ?, @nvarchar6 = ?, @nvarchar3 = ?, @nvarchar4 = ?, @nvarchar5 = ?, @nvarchar6 = ?, @nvarchar7 = ?, @nvarchar8 = ?, @nvarchar9 = ?, @nvarchar10 = ?, @nvarchar11 = ?, @nvarchar12 = ?, @nvarchar13 = ?, @nvarchar14 = ?, @nvarchar15 = ?, @nvarchar16 = ?, @nvarchar17 = ?, @nvarchar18 = ?, @int2 = ?, @nvarchar35 = ?, @datetime1 = ?, @datetime2 = ?, @datetime3 = ?, @datetime4 = ?, @datetime5 = ?, @date...
Unexpected ...time6 = ?, @datetime7 = ?, @datetime8 = ?, @float1 = ?, @nvarchar36 = ?, @int3 = ?, @ntext2 = ?, @int4 = ?, @int5 = ?, @int6 = ?, @int7 = ?, @int8 = ?, @int9 = ?, @int10 = ?, @ntext3 = ?, @nvarchar37 = ?, @tp_ID = ?, @tp_ContentType = ?, @tp_Modified = ?, @tp_Created = ?, @tp_ModerationStatus = ?, @Size = 266, @ExtraItemSize = @ExtraItemSize ,@ItemName=N'UKSH',@acl=0xF3FE000001000000000000000C00000001000000001001083000000002000000FFFFFFFFFFFFFF7F0300000041104308B000000004000000FFFFFFFFFFFFFF7F0500000061104308B000000006000000EF12433CB001000007000000001001083000000008000000FF1B5F3CB001000009000000EF1BE77EF00100400A000000FF13433CB00100000B00000021100308300000000C0000000010010830000000; IF @@iRet <> 0 BEGIN ROLLBACK TRAN; GOTO DONE; END SELECT @ExtraItemSize = 0 EXEC @@iRet = proc_AddListItem...
Unexpected ... @SiteId = '91713DD8-88FA-448A-8596-67313E781F4F',@WebId='0770642C-837D-4897-AF07-1B28D3F0C212',@ListID = 'F9870FF9-DA52-40F3-A77A-80D98A7F461B',@RowOrdinal = 1,@ItemDocType = 0,@ItemId = @ItemId OUTPUT,@ItemDirName=@DN OUTPUT,@ItemLeafName=@LN OUTPUT,@UserID = 1,@TimeNow = '20080702 13:40:20',@ServerTemplate = 100,@Basetype= 0,@Level= 1,@tp_GUID ='03863A1B-2194-41FC-911F-D85A480DC4B8',@AddNamespace=1,@CheckDiskQuota=1, @datetime1 = ?, @Size = 0, @ExtraItemSize = @ExtraItemSize ,@ItemName=N'UKSH',@acl=0xF3FE000001000000000000000C00000001000000001001083000000002000000FFFFFFFFFFFFFF7F0300000041104308B000000004000000FFFFFFFFFFFFFF7F0500000061104308B000000006000000EF12433CB001000007000000001001083000000008000000FF1B5F3CB001000009000000EF1BE77EF00100400A000000FF13433CB00100000B00000021100308300...
Unexpected ...000000C0000000010010830000000; IF @@iRet <> 0 BEGIN ROLLBACK TRAN; GOTO DONE; END EXEC proc_ClearLinks @@S,@DN,@LN,@@Level,'6BA51930-9043-4ACC-8783-27C3FE29B6C8'; EXEC proc_ClearLinks @@S,@DN,@LN,@@Level,'15877298-3228-4D5B-A5A5-E45D53BCBC67';COMMIT TRAN; DONE: SELECT @@iRet, @ItemId "
Medium Unknown SPRequest error occurred. More information: 0x80040e14
An "nvarchar3" konnte ich mich erinnern, das taucht als Wert beim Attribut ColName in der extrahierten Felddefinition für das BDC-Feld auf:

Und da ging mir dann das Licht auf: wir hatten im Laufe der letzten Wochen öfter einige Änderungen an den BDC-Feldern vorgenommen, bzw. neue hinzugefügt, alte gelöscht usw.
Und natürlich nicht jedes mal alle Feld neu extrahiert sondern immer nur die veränderten.

Dadurch existierten dann im Code tatsächlich mehrere Definitionen unterschiedlicher BDC-Felder mit den Attributen ColName="nvarchar3".

Daraufhin änderten wir alle nvarcharXX-Einträge so ab, dass von oben nach unten nun die Zahlen in aufsteigender Reihenfolge vergeben wurden, also nvarchar1, nvarchar2, etc.

Et vóila: der Fehler war beseitigt! :-)

Darauf müssen wir aufpassen, wenn wir bei späteren Change Requests weitere BDC-Felder hinzufügen, verändern oder was auch immer.

Nachtrag: Wer lesen kann, ist klar im Vorteil: das WSS-SDK sagt zu ColName folgendes:

"Optional Text. An internal attribute that defines the mapping of the field to the physical storage name for this field. This must be a valid name in the underlying database and must be identical to the name used in the database table. If not specified, the server generates a column name that does not collide with any existing column names and that contains only characters that are allowed by Microsoft SQL Server."

Wenn wir dieses Attribut also komplett aus sämtlichen unserer Felddefinitionen entfernen, sollten wir weder jetzt noch bei zukünftigen Updates Probleme damit bekommen.